Di chuyển đến mặt trước ASCII có thể in


19

Lý lịch

Biến đổi di chuyển về phía trước (MTF) là một thuật toán mã hóa dữ liệu được thiết kế để cải thiện hiệu suất của các kỹ thuật mã hóa entropy.

Trong thuật toán nén bzip2 , nó được áp dụng sau khi biến đổi Burrows của Wheeler (như được thấy trong Burrows, Wheeler và Back ), với mục tiêu biến các nhóm ký tự lặp lại thành các số nguyên không âm nhỏ, dễ nén.

Định nghĩa

Với mục đích của thử thách này, chúng tôi sẽ xác định phiên bản ASCII có thể in của MTF như sau:

Cho một chuỗi đầu vào s , lấy một mảng trống r , chuỗi d của tất cả các ký tự ASCII có thể in (0x20 đến 0x7E) và lặp lại các điều sau cho mỗi ký tự c của s :

  1. Nối chỉ số của c trong d vào r .

  2. Di chuyển c đến phía trước của d , nghĩa là xóa c khỏi d và đưa nó vào phần còn lại.

Cuối cùng, chúng tôi lấy các phần tử của r làm chỉ mục trong d gốc và tìm nạp các ký tự tương ứng.

Ví dụ từng bước

INPUT: "CODEGOLF"

0. s = "CODEGOLF"
   d = " !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = []
1. s = "ODEGOLF"
   d = "C !\"#$%&'()*+,-./0123456789:;<=>?@ABDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35]
2. s = "DEGOLF"
   d = "OC !\"#$%&'()*+,-./0123456789:;<=>?@ABDEFGHIJKLMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47]
3. s = "EGOLF"
   d = "DOC !\"#$%&'()*+,-./0123456789:;<=>?@ABEFGHIJKLMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47 37]
4. s = "GOLF"
   d = "EDOC !\"#$%&'()*+,-./0123456789:;<=>?@ABFGHIJKLMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47 37 38]
5. s = "OLF"
   d = "GEDOC !\"#$%&'()*+,-./0123456789:;<=>?@ABFHIJKLMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47 37 38 40]
6. s = "LF"
   d = "OGEDC !\"#$%&'()*+,-./0123456789:;<=>?@ABFHIJKLMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47 37 38 40 3]
7. s = "F"
   d = "LOGEDC !\"#$%&'()*+,-./0123456789:;<=>?@ABFHIJKMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47 37 38 40 3 45]
8. s = ""
   d = "FLOGEDC !\"#$%&'()*+,-./0123456789:;<=>?@ABHIJKMNPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~"
   r = [35 47 37 38 40 3 45 41]

OUTPUT: "COEFH#MI"

Bài tập

Viết chương trình hoặc hàm thực hiện ASCII MTF có thể in được (như được định nghĩa ở trên).

Các trường hợp thử nghiệm

Input:  Programming Puzzles & Code Golf
Output: Prpi"do lp%((uz rnu&3!P/o&$U$(p

Input:  NaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaN BATMAN!
Output: Na! !! !! !! !! !! !! !! !! !! !! !! !! !! !! !!"DDUP"%'

Input:  Two more questions and I have bzip2 in less than 100 bytes!
Output: Twp#o"si$sv#uvq(u$(l#o#W!r%w+$pz,xF%#,"x(. #0--'$GG ".z(**:

Quy tắc bổ sung

  • Bạn không thể sử dụng bất kỳ toán tử tích hợp nào tính toán MTF của chuỗi.

  • Mã của bạn có thể in một dòng mới theo dõi nếu bạn chọn STDOUT cho đầu ra.

  • Mã của bạn phải hoạt động cho bất kỳ đầu vào nào có 1000 ký tự ASCII có thể in hoặc ít hơn (0x20 đến 0x7E).

  • Quy tắc golf tiêu chuẩn áp dụng. Đệ trình ngắn nhất tính bằng byte thắng.


1
"Nanananana DDUP!" không hấp dẫn như "Người dơi!" ...
Doorknob

8
@Doorknob: Nhưng Batman không dễ nén.
Dennis

Chúng ta có thể xuất kết quả trong một hàm trả về thay vì in nó sang STDOUT không?
Gây tử vong vào

@Firthize: Đó là hình thức đầu ra tự nhiên nhất cho các hàm, vì vậy, có. Nhân tiện, chúng tôi có mặc định cho I / O , vì vậy trừ khi câu hỏi nói khác đi, điều đó luôn được cho phép.
Dennis

Câu trả lời:


6

CJam, 20

'¡,q{_C#c' ,C+@|}fC;

Dùng thử trực tuyến

Giải trình:

'¡,      make a string of characters with codes from 0 to 160 (a modified "d")
         could have been to 126 but stackexchange doesn't like the DEL character
q        read the input (s)
{…}fC    for each character C in s
  _      duplicate the d string
  C#     find the index of C in d
  c      convert to character (this is the result)
  ' ,    make a string of characters from 0 to 31
  C+     append C to the string
  @      bring d to the top
  |      set union, preserving order; effectively, C is moved to position 32
         this is the updated d string
;        pop the last d

6

Đà điểu , 46 45 ký tự

Không có số phiên bản trong tiêu đề vì đây thực sự chỉ là cam kết mới nhất . Tôi đã thêm toán tử O(mã ascii vào chuỗi) sau khi phát hành phiên bản mới nhất (nhưng vẫn còn trước khi thử thách này được đăng).

{a95,{32+O}%:d3@{:x\.3@?3@\+\x-x\+}/;{d=}%s*}

Giải trình:

a             this is the "r" array (a is short for [], empty array)
95,{32+O}%:d  this is the "d" array
3@{...}/      for each character in the input (as an "argument")...
  :x            store in variable x (stack is now [r d c])
  \.3@?         find index in d     (stack is now [r d idx])
  3@\+          append index to r   (stack is now [d modified_r])
  \x-           remove char from d, and then...
  x\+           prepend char to d   (stack is now [modified_r modified_d])
;             throw away modified_d
{d=}%         map r to indices of (original) d
s*            join (s is short for ``, empty string)

Tôi tự hỏi liệu PPCG có đang chuyển từ "mã hóa nhiệm vụ này theo cách dễ hiểu nhất có thể bằng ngôn ngữ yêu thích của bạn" sang "thiết kế ngôn ngữ lập trình của riêng bạn để giải quyết nhiệm vụ golf mã điển hình ngắn hơn so với golf"
John Dvorak

1
@AlexA. ... Đợi đã, huh, nó đánh vần theo cách đó? toàn bộ cuộc sống của tôi là một lời nói dối
Doorknob

@JanDvorak Đà điểu gần giống với GolfScript. Chỉ có lý do thực sự tôi tạo ra là vì a.) GolfScript khó chịu không có REPL và b.) Có một vài toán tử / tính năng bị thiếu (dấu phẩy động, I / O, v.v.). Và thiết kế ngôn ngữ là niềm vui nào!
tay nắm cửa

3

Con trăn 3, 88

*d,=range(127)
for c in input():y=d.index(ord(c));d[:32]+=d.pop(y),;print(chr(y),end='')

Sử dụng một số ý tưởng từ giải pháp CJam của tôi.
-4 byte thuộc về Sp3000 :)


2

SWI-Prolog, 239 197 189 byte

a(S):-l([126],X),a(S,X,[],R),b(R,X).
a([A|T],X,S,R):-nth0(I,X,A,Z),(a(T,[A|Z],[I|S],R);R=[I|S]).
b([A|T],X):-(b(T,X);!),nth0(A,X,E),put(E).
l([B|R],Z):-A is B-1,X=[A,B|R],(A=32,Z=X;l(X,Z)).

Ví dụ: a(`Two more questions and I have bzip2 in less than 100 bytes!`).đầu ra:

Twp#o"si$sv#uvq(u$(l#o#W!r%w+$pz,xF%#,"x(. #0--'$GG ".z(**:

(và true .sau đó, rõ ràng)

Lưu ý: phiên bản SWI-Prolog của bạn phải là một trong những phiên bản mới hơn trong đó backquote `đại diện cho chuỗi mã. Các chuỗi mã được sử dụng để được biểu thị bằng dấu ngoặc kép "trong các phiên bản cũ hơn.


2

Con trăn 2, 137 110 104

Không khó để thực hiện, nhưng có lẽ vẫn có thể chơi được?

Hãy thử nó ở đây

e=d=map(chr,range(32,127))
r=""
for c in raw_input():n=e.index(c);r+=d[n];e=[e[n]]+e[:n]+e[n+1:]
print r

1
Tôi nghĩ rằng bạn nên làm một bản đồ danh sách e=d=map(chr,range(32,127))trong Python 2, mặc dù bạn phải điều chỉnh eđể xử lý một danh sách.
xnor

@xnor Cảm ơn. Tôi cũng đã thử sử dụng e=[e.pop(n)]+e, nhưng nó không hoạt động. Tại sao vậy?
mbomb007

Bạn đã có e=d=, vì vậy khi bạn bật từ ebạn cũng xuất hiện d. Hãy thử d=e[:].
Sp3000

1
Nhưng tại thời điểm này có lẽ tốt hơn là chỉ nên làm n=e.index(ord(c));r+=chr(n+32);và thảd
Sp3000

1

Bình thường, 24 byte

JK>95CM127s@LKxL~J+d-Jdz

Trình diễn. Khai thác thử nghiệm.

Các bit đầu tiên. JK>95CM127thiết lập danh sách cần thiết và lưu nó vào JK. ~J+d-Jdthực hiện cập nhật danh sách, trong khi xL ... zánh xạ các ký tự đầu vào đến vị trí của chúng trong danh sách. Cuối cùng, s@LKchuyển đổi các chỉ mục đó thành các ký tự trong danh sách ban đầu.


1

Haskell, 120 byte

e#s=[b|(b,a)<-zip[0..]s,a==e]!!0
a=[' '..'~']
f=snd.foldl(\(d,r)e->(e:take(e#d)d++tail(drop(e#d)d),r++[a!!(e#d)]))(a,[])

Ví dụ sử dụng: f "CODEGOLF"->"COEFH#MI"

Cách thức hoạt động: #là một hàm chỉ mục trả về vị trí etrong s(không thể sử dụng nguồn gốc của Haskell elemIndexvì đắt tiền import). Hàm chính ftheo một mẫu gấp trong đó nó cập nhật chuỗi vị trí dvà chuỗi kết quả rkhi nó đi qua chuỗi đầu vào.

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.