Viết chương trình đưa ra mức độ phản chiếu của nó


31

Có 95 ký tự ASCII có thể in :

 !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~

Trong phông chữ Consolas (mặc định khối mã Stack Exchange), một số ký tự có các gương xung quanh trục đối xứng dọc:

  • Những cặp nhân vật này là tấm gương của nhau: () [] {} <> /\
  • Các ký tự này là gương của chính họ: ! "'*+-.8:=AHIMOTUVWXY^_ovwx|(Lưu ý rằng không gian là một.)
  • Những cái này không có gương: #$%&,012345679;?@BCDEFGJKLNPQRSZ`abcdefghijklmnpqrstuyz~

( i, l, 0, #, Và có lẽ nhân vật khác là gương của mình trong một số phông chữ nhưng chúng tôi sẽ dính vào các hình dạng Consolas.)

Một chuỗi được gọi là một gương của chính nó nếu nó được tạo ra chỉ với 39 ký tự gương , được sắp xếp sao cho chuỗi có một đường đối xứng dọc ở giữa. Vì vậy, ](A--A)[là một tấm gương của chính nó nhưng ](A--A(]không.

Viết chương trình một dòng chẵn có một bản sao của chính nó. Khi N bản sao của nửa bên trái của nó đã được thêm vào nó và N bản sao của nửa bên phải của nó đã được thêm vào nó, nó sẽ tạo ra N + 1. N là số nguyên không âm.

Ví dụ: nếu chương trình là ](A--A)[(nửa bên trái : ](A-, nửa bên phải -A)[:), thì:

  • Chạy ](A--A)[nên đầu ra 1. (N = 0)
  • Chạy ](A-](A--A)[-A)[nên đầu ra 2. (N = 1)
  • Chạy ](A-](A-](A--A)[-A)[-A)[nên đầu ra 3. (N = 2)
  • Chạy ](A-](A-](A-](A--A)[-A)[-A)[-A)[nên đầu ra 4. (N = 3)
  • . . .
  • Chạy ](A-](A-](A-](A-](A-](A-](A-](A-](A-](A--A)[-A)[-A)[-A)[-A)[-A)[-A)[-A)[-A)[-A)[nên đầu ra 10. (N = 9)
  • v.v.

Quy tắc

  • Xuất ra thiết bị xuất chuẩn hoặc ngôn ngữ thay thế gần nhất của bạn. Có thể có một dòng mới tùy chọn. Không có đầu vào nên được thực hiện.
  • Về mặt lý thuyết, quy trình sẽ hoạt động cho N lên tới 2 15 -1 hoặc hơn thế nữa, với đủ bộ nhớ và khả năng tính toán.
  • Một chương trình đầy đủ là bắt buộc, không chỉ là lệnh REPL .

Chương trình ban đầu ngắn nhất (trường hợp N = 0) tính bằng byte thắng.


Trong một số phông chữ, #cũng là mối quan hệ riêng của nó, nhưng, bạn nói đúng, không phải trong consolas.
SuperJedi224

1
Sử dụng thay thế được phép? Nói cách khác: chúng ta nên viết một chương trình hợp lệ hoàn chỉnh hay một biểu thức là đủ? Tôi đang nghĩ về mục Haskell sẽ hoạt động khi chạy trong ghci nhưng không phải là một chương trình hoàn chỉnh hợp lệ.
Bakuriu

@Bakuriu Một chương trình đầy đủ là bắt buộc. Câu trả lời của Haskell không hợp lệ.
Sở thích của Calvin

4
Tại sao không phải là gương 'b' và 'd' của nhau? Nó làm cho kế hoạch của tôi không thể thực hiện được: P
Thijs ter Haar

1
@ThijsterHaar Tôi thực sự đã không cân nhắc điều đó nhưng có vẻ như hình dạng Consolas của họ chỉ hơi khác một chút, xin lỗi: P
Sở thích của Calvin

Câu trả lời:


20

Pip, 12 8 4 byte

Bây giờ với ít hơn 66% byte!

x++x
  • xlà một biến, được khởi tạo trước "". Trong bối cảnh số, điều này trở thành 0.
  • Nửa đầu, sans cuối cùng +, làm cho một biểu thức của hình thức x+x+...+x. Đây là một tuyên bố hợp lệ mà không làm gì.
  • Nửa thứ hai, bao gồm cả trận chung kết +từ nửa đầu, tạo ra một biểu hiện của hình thức ++x+x+...+x. ++xincrements xđến 1, và phần còn lại cho biết thêm nó vào chính nó N lần. Vì các biểu thức được đánh giá từ trái sang phải trong Pip, nên mức tăng được đảm bảo xảy ra trước tiên và kết quả bằng với số cấp độ gương.
  • Cuối cùng, giá trị của biểu thức này là tự động in.

Thật không may, Pip không xử lý tốt các biểu thức lớn: giải pháp này gây ra maximum recursion depth exceededlỗi cho N trên 500 hoặc hơn. Đây là một giải pháp trước đó không, cho 8 byte :

x++oo++x

Thêm về Pip


OK, trừ khi ai đó đăng câu trả lời 2 byte, có vẻ như bạn đã có câu trả lời này trong túi. Nhân tiện, tôi không biết liệu bạn có chạy nó với N = 32767 không , nhưng sản lượng thực tế là Fatal error: maximum recursion depth exceeded while calling a Python object.
Dennis

@Dennis Vâng, tôi thực sự gặp phải điều đó - nó bắt đầu khá sớm, khoảng 600 nếu không phải trước đó. Lý do là các biểu thức được đánh giá bằng cách đánh giá đệ quy tất cả các biểu thức con trước, do đó x+x+...+xtạo ra độ sâu đệ quy O (N). Có lẽ điều đó làm mất hiệu lực câu trả lời này. Tôi sẽ thêm một ghi chú.
DLosc

Giới hạn đệ quy có thể dễ dàng điều chỉnh trong Python, phải không?
Dennis

@Dennis Có, mặc dù có những cảnh báo nghiêm trọng về những gì nó sẽ làm với hệ thống của bạn nếu bạn đặt nó quá cao, vì vậy tôi chưa bao giờ thử nó. ;) Bên cạnh đó, việc định cấu hình không thể thực hiện được từ bên trong Pip , vì vậy có vẻ như tôi đang lừa dối tôi. Tuy nhiên, nếu bạn muốn dùng thử, tôi rất muốn nghe kết quả.
DLosc

Tôi đã thử. Trên máy của tôi, tăng giới hạn đệ quy lên 20000 segfaults. Nhưng vì câu trả lời chỉ hoạt động khi có đủ bộ nhớ và khả năng tính toán , nên đó không phải là vấn đề.
Dennis

34

GolfScript, 10 byte

!:{)::(}:!

Dùng thử trực tuyến với Web Golfscript: N = 0 , N = 1 , N = 2 , N = 3 , N = 41

Web GolfScript có giới hạn 1024 ký tự, nhưng trình thông dịch Ruby xử lý hoàn hảo N = 32767 :

$ curl -Ss http://www.golfscript.com/golfscript/golfscript.rb > golfscript.rb
$ echo '"!:{):"32768*":(}:!"32768*' | ruby golfscript.rb > mirror-level-32767.gs
$ ruby golfscript.rb mirror-level-32767.gs
32768

Làm thế nào nó hoạt động

Không có bất kỳ đầu vào nào, ban đầu GolfScript có một chuỗi trống trên ngăn xếp.

Trong nửa đầu bên trái, điều sau đây xảy ra:

  • !áp dụng logic KHÔNG cho chuỗi rỗng. Điều này đẩy 1.

  • :{lưu số nguyên trên ngăn xếp trong biến {.

    Có, đó là một định danh hợp lệ, mặc dù không có cách nào để lấy giá trị được lưu trữ.

  • ) tăng số nguyên trên ngăn xếp.

  • : là một hướng dẫn không đầy đủ.

Các nửa bên trái tiếp theo, xảy ra như sau:

  • :!(nơi :còn sót lại từ trước) lưu số nguyên trên ngăn xếp trong biến !.

    Vâng, đó cũng là một định danh hợp lệ. Điều này phá vỡ !lệnh, nhưng chúng tôi không sử dụng nó nữa.

  • :{, ):làm việc như trước đây.

Trong nửa đầu bên phải, điều sau đây xảy ra:

  • ::(nơi :còn sót lại từ trước) lưu số nguyên trên ngăn xếp trong biến :.

    Vâng, thậm chí đó là định danh hợp lệ. Như với {, không có cách nào để lấy lại giá trị được lưu trữ.

  • ( giảm số nguyên trên ngăn xếp, thu được số nửa còn lại.

  • }, vì nó là vô song và chấm dứt thực hiện ngay lập tức.

    Đây là một tính năng không có giấy tờ. Tôi gọi chúng là siêu phẩm .

Các mã còn lại chỉ đơn giản là bỏ qua.


Có vẻ như thực sự kỳ lạ khi có một }nửa chưa từng có trong nửa sau mã của bạn trong một cuộc thi nhân bản.
ballesta25

Đó là một mẹo phổ biến trong các biến thể palindrom. Trong "\""/", trích dẫn kép thứ tư cũng sẽ không thể so sánh được vì câu thứ hai đã được thoát.
Dennis

27

Mã máy Z80, 8 6 byte *

<8ww8> * Giả sử một số điều kiện bằng cách nhập từ Amstrad BASIC

<   INC A         // A=A+1
8w  JR C, #77     ## C is unset unless A has overflowed, does nothing

w   LD (HL), A    // Saves A to memory location in HL (randomly initialised)
8>  JR C, #3E     ## C is still unset, does nothing

Aban đầu là 0 khi được nhập từ BASIC. Nó tăng A n lần, sau đó ghi n lần vào cùng một vị trí bộ nhớ (được đặt ở vị trí hơi ngẫu nhiên theo BASIC)! Hoạt động JRJump Relative không bao giờ thực hiện bất cứ điều gì vì Ccờ luôn không được đặt, do đó được sử dụng để "nhận xét" byte sau đây! Phiên bản này hơi gian lận bằng cách giả sử một số điều kiện nhập cảnh, cụ thể là nhập từ BASIC đảm bảo Aluôn là 0. Vị trí của (HL)không được đảm bảo an toàn, và trên thực tế, có lẽ là một vị trí nguy hiểm. Đoạn mã dưới đây mạnh mẽ hơn nhiều, đó là lý do tại sao nó dài hơn nhiều.

Mã máy Z80, 30 byte

Như ASCII: o!.ww.!>A=o>{))((}<o=A<!.ww.!o

Về cơ bản, nửa đầu đảm bảo tạo ra giá trị 0 và nửa sau tăng nó và ghi vào bộ nhớ. Trong phiên bản mở rộng dưới đây ##biểu thị mã không phục vụ mục đích trong một nửa gương của nó.

o   LD L, A       ## 
!.w LD HL, #772E  // Load specific address to not corrupt random memory!
w   LD (HL), A    ## Save random contents of A to memory
.!  LD L, #21     ## 
>A  LD A, #41     // A=#41
=   DEC A         // A=#40
o   LD L, A       // L=#40
>{  LD A, #7B     ## 
)   ADD HL, HL    // HL=#EE80
)   ADD HL, HL    // HL=#DD00. L=#00 at this point

((  JR Z, #28     ## 
}   LD A, L       // A=L
<   INC A         // A=L+1
o   LD L, A       // L=L+1
=   DEC A         // A=L
A   LD B, C       ## 
<   INC A         // A=L+1
!.w LD HL, #772E  // Load address back into HL
w   LD (HL), A    // Save contents of A to memory
.!  LD L, #21     ## 
o   LD L, A       // L=A

Phân tích các hướng dẫn được phép:

n   op    description
--  ----  -----------
28  LD    LoaD 8-bit or 16-bit register
3   DEC   DECrement 8-bit or 16-bit register
1   INC   INCrement 8-bit or 16-bit register
1   ADD   ADD 8-bit or 16-bit register

Available but useless instructions:
3   JR    Jump Relative to signed 8-bit offset
1   DAA   Decimal Adjust Accumulator (treats the A register as two decimal digits
          instead of two hexadecimal digits and adjusts it if necessary)
1   CPL   1s ComPLement A
1   HALT  HALT the CPU until an interrupt is received

Trong số 39 hướng dẫn được phép, 28 là các hoạt động tải (khối từ 0x40 đến 0x7F đều là các lệnh đơn byte LD), hầu hết trong số đó không có trợ giúp ở đây! Tải duy nhất vào lệnh bộ nhớ vẫn được phép là LD (HL), Ađiều đó có nghĩa là tôi phải lưu trữ giá trị trong A. Vì Alà đăng ký duy nhất còn lại với một INChướng dẫn được phép, điều này thực sự khá tiện dụng!

Tôi không thể tải Avới 0x00 để bắt đầu vì ASCII 0x00 không phải là ký tự được phép! Tất cả các giá trị khả dụng khác xa 0 và tất cả các hướng dẫn toán học và logic đã không được phép! Ngoại trừ ... tôi vẫn có thể làm ADD HL, HL, thêm 16-bit HLcho chính nó! Ngoài việc tải trực tiếp các giá trị (không sử dụng ở đây!), Tăng Avà giảm giá A, Lhoặc HLđây là cách duy nhất tôi có để thay đổi giá trị của một thanh ghi! Thực sự có một hướng dẫn chuyên biệt có thể hữu ích trong nửa đầu nhưng một nỗi đau phải làm việc trong nửa sau và một hướng dẫn bổ sung gần như vô dụng ở đây và sẽ chỉ chiếm không gian.

Vì vậy, tôi tìm thấy giá trị gần nhất với 0 Tôi có thể: 0x41. Làm thế nào là gần 0? Trong nhị phân, nó là 0x01000001. Vì vậy, tôi giảm nó, tải nó vào Lvà làm ADD HL, HLhai lần! Lbây giờ là số không, mà tôi tải lại vào A! Thật không may, mã ASCII cho ADD HL, HL)vì vậy bây giờ tôi cần sử dụng (hai lần. May mắn thay, (được JR Z, e, nơi elà byte tiếp theo. Vì vậy, nó ngấu nghiến byte thứ hai và tôi chỉ cần chắc chắn rằng nó không làm gì bằng cách cẩn thận với Zcờ! Hướng dẫn cuối cùng ảnh hưởng đến Zcờ là DEC A(theo trực giác, ADD HL, HLkhông thay đổi nó) và vì tôi biết rằng đó Alà 0x40 tại thời điểm đó, nó được đảm bảo rằng Znó không được đặt.

Lệnh đầu tiên trong nửa thứ hai JR Z, #28sẽ không làm gì 255 lần đầu tiên vì cờ Z chỉ có thể được đặt nếu A đã tràn từ 255 xuống 0. Sau đó, đầu ra sẽ bị sai, tuy nhiên vì dù sao nó chỉ lưu các giá trị 8 bit không nên quan trọng Mã không nên được mở rộng hơn 255 lần.

Mã phải được thực thi như một đoạn trích vì tất cả các cách có sẵn để trả lại sạch sẽ không được phép. Tất cả các hướng dẫn RETurn đều trên 0x80 và một vài thao tác Jump được phép chỉ có thể chuyển sang phần bù dương, bởi vì tất cả các giá trị âm 8 bit cũng không được phép!


6
GÌ. CÁI GÌ THẾ NÀY.
đám mây

4
Bây giờ tôi đã thấy câu trả lời này, sử dụng GolfScript / J / vv. chỉ có vẻ như gian lận. : p
cloudfeet 29/05/2015

Có bộ xử lý tương thích Z80 với thanh ghi A 16 bit không? Tôi đang hỏi vì câu hỏi yêu cầu mã phải hoạt động với N = 32767 .
Dennis

1
@Dennis Để chương trình hoạt động với N = 32767, nó phải dài ít nhất 2 x 32767 hoặc 65534 byte. Z80 chỉ có thể giải quyết 65536 byte bộ nhớ, khiến điều này trở thành một nhiệm vụ bất khả thi vì tôi không tin rằng tôi có thể làm cho chương trình nhỏ hơn 6 byte! Thanh Aghi luôn là 8 bit, nếu không bộ xử lý sẽ không tương thích với Z80. Tôi muốn nói rằng được cung cấp đủ bộ nhớ và khả năng tính toán đã được đề cập ở đây!
CJ Dennis

1
@Dennis Bạn hiểu tại sao không có bộ xử lý tương thích Z80 sẽ có một Athanh ghi của bất cứ thứ gì ngoài 8 bit? Thay đổi nó thành 16 bit sẽ phá vỡ mã dựa trên 255 + 1 = 0 chẳng hạn. Bạn sẽ phải phát minh ra CPU, hãy gọi nó là Z160, sử dụng thanh ghi 16 bit mặc định nhưng vẫn sử dụng cùng một lệnh 8 bit được đặt từ Z80. Kỳ dị!
CJ Dennis

19

J, 16 14 byte

(_=_)]++[(_=_)

Tập quán:

   (_=_)]++[(_=_)
1
   (_=_)]+(_=_)]++[(_=_)+[(_=_)
2
   (_=_)]+(_=_)]+(_=_)]++[(_=_)+[(_=_)+[(_=_)
3

Giải trình:

  • J đánh giá từ phải sang trái.

  • (_=_)inf equals infđúng, có giá trị 1, vì vậy biểu thức trở thành 1+]...[+1. ( (8=8)cũng sẽ làm việc nhưng điều này có vẻ mát mẻ hơn. :))

  • []trả về các đối số trái và phải tương ứng nếu chúng có 2 đối số. Nếu họ chỉ nhận được 1 thì họ trả lại.

  • +thêm 2 đối số. Nếu nó chỉ được 1 thì nó trả về.

Bây giờ hãy đánh giá biểu thức cấp 3 (đi từ phải sang trái):

(_=_)]+(_=_)]++[(_=_)+[(_=_)  NB. (_=_) is 1

1]+1]+1]++[1+[1+[1  NB. unary [, binary +

1]+1]+1]++[1+[2  NB. unary [, binary +

1]+1]+1]++[3  NB. unary [, unary +

1]+1]+1]+3  NB. unary +, binary ]

1]+1]+3  NB. unary +, binary ]

1]+3  NB. unary +, binary ]

3

Như chúng ta thấy một nửa bên phải của 1được thêm vào và bên trái của 1'bị bỏ qua dẫn đến số nguyên mong muốn N, mức độ gương.

Hãy thử trực tuyến tại đây.


12

Haskell, 42 byte

(8-8)-(-(8-8)^(8-8))--((8-8)^(8-8)-)-(8-8)

May mắn thay, một nhận xét dòng trong Haskell (-> --) là có thể phản chiếu và một nửa của nó (-> -) là một chức năng hợp lệ. Phần còn lại là một số toán học để có được các số 01. Về cơ bản chúng tôi có (0)-(-1)một nhận xét N=0và trả trước (0)-(-1)-trong từng bước.

Nếu số dấu phẩy động được phép cho đầu ra, chúng ta có thể xây dựng 1từ 8/8và lấy bằng 26 byte:

Haskell, 26 byte

(8-8)-(-8/8)--(8\8-)-(8-8)

Kết quả đầu ra 1.0, 2.0vv


2
Điều này là không hợp lệ về mặt kỹ thuật vì nó phải là một chương trình đầy đủ.
Sở thích của Calvin

@ Calvin'sHob sở thích: Tôi hiểu. Chúng ta có đồng thuận về các yêu cầu tối thiểu cho một chương trình đầy đủ không? Tôi đã tìm kiếm meta, nhưng chỉ tìm thấy một cuộc thảo luận về các chức năng, không phải các chương trình. Tùy thuộc vào định nghĩa của một chương trình đầy đủ, tôi có thể sửa giải pháp của mình.
nimi

Tôi sẽ gọi nó là một chương trình đầy đủ nếu bạn có thể lưu nó trong một tệp program.hsvà sau đó chạy $ runhaskell program.hstừ dòng lệnh và xem đầu ra. Tôi không biết Haskell vì vậy tôi không thể nói chính xác những gì cần thay đổi.
Sở thích của Calvin

2
@ Calvin'sHobbies: runhaskelllà một tập lệnh shell thiết lập một số môi trường và cuối cùng gọi ghc, trình biên dịch Haskell. Bạn có thể chạy mã của tôi trực tiếp với ghc: ghc -e "(8-8)-(-8/8)--(8\8-)-(8-8)". Điều này khởi chạy ghcđể đánh giá mã được cung cấp dưới dạng đối số, in kết quả và thoát. Không REPL, không tương tác. Tất nhiên điều này sẽ thêm +1 vào số byte cho -e.
nimi

@nimi: -ekhông đóng góp vào điểm số trong trường hợp này. Chúng tôi không đếm byte cho perl -Ehoặc gcc -std=c99.
Dennis

11

CJam, 14 byte

]X+:+OooO+:+X[

Dùng thử trực tuyến trong trình thông dịch CJam: N = 0 , N = 1 , N = 2 , N = 3 , N = 41

Lưu ý rằng mã này kết thúc với một thông báo lỗi. Sử dụng trình thông dịch Java, thông báo lỗi đó có thể được loại bỏ bằng cách đóng hoặc chuyển hướng STDERR. 1

Làm thế nào nó hoạt động

Ở nửa bên trái, điều sau đây xảy ra:

  • ] kết thúc toàn bộ ngăn xếp trong một mảng.

  • Xnối 1vào mảng đó.

  • :+ tính tổng của tất cả các phần tử mảng.

  • Oo in nội dung của mảng trống (nghĩa là không có gì).

Trong nửa đầu bên phải, điều sau đây xảy ra:

  • o in số nguyên trên ngăn xếp, là đầu ra mong muốn.

  • O+ cố gắng nối một mảng trống vào mục trên cùng của ngăn xếp.

    Tuy nhiên, ngăn xếp trống rỗng trước khi đẩy O. Điều này thất bại và chấm dứt việc thực hiện chương trình.

Các mã còn lại chỉ đơn giản là bỏ qua.

1 Theo cuộc thăm dò ý kiến, các bài nộp có được phép thoát ra khi có lỗi không? , điều này được cho phép.


Tôi nghi ngờ về việc chấp nhận điều này do lỗi, nhưng vì nó không chiến thắng nên tôi không quá quan tâm.
Sở thích của Calvin

Các nhiệm vụ như thế này cực kỳ khó khăn trong CJam, vì cho rằng đó là ngôn ngữ chơi gôn. Ngay cả một lỗi cú pháp (ví dụ, một toán tử không xác định) trong một khối chưa được thực hiện sẽ ngăn toàn bộ chương trình thực thi. Tôi vẫn đang cố gắng để thoát khỏi lỗi.
Dennis
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.