Nhảy và chạy


18

Matthew thích giải câu đố. Bất cứ khi nào anh ta giải quyết được một, anh ta vui vẻ bỏ qua. Gần đây anh ấy thực sự cần phải làm điều này vì một trận mưa sao băng đã mở các miệng hố và lỗ hổng trên mặt đất mà anh ấy không muốn rơi xuống.

Bạn được ban cho một phần của phong cảnh mà Matthew muốn băng qua, hy vọng cuối cùng sẽ khỏe mạnh. Mặt đất được tính theo mét, với mỗi mét là mặt đất bình thường hoặc lỗ. Khi anh ta đang chạy, anh ta cố gắng vượt qua một mét mỗi bước; thay thế là nhảy qua bốn mét mỗi bước. Matthew bắt đầu ở phía xa bên trái trên đồng hồ mặt đất đầu tiên và muốn đến cái cuối cùng (mặc dù không vượt ra ngoài - chỉ cần tưởng tượng một lỗ hổng vô tận vượt ra khỏi mét cuối cùng được đưa ra trong cảnh quan).

Đầu vào

Đầu vào được đưa ra dưới dạng một dòng trên đầu vào tiêu chuẩn, được kết thúc bằng ngắt dòng. Dòng này bao gồm dấu gạch ngang ( -) hoặc dấu gạch dưới ( _), tương ứng với đồng hồ đo mặt đất hoặc lỗ. Một đầu vào mẫu có thể là:

----__--___---

Cảnh quan đã cho ít nhất là một và dài tối đa 30 mét và luôn bắt đầu bằng mặt đất.

Đầu ra

Đầu ra được đưa ra trên đầu ra tiêu chuẩn và đại diện cho một loạt các lệnh chuyển động cho Matthew, hoặc là run ( R) hoặc jump ( J). Như đã nói ở trên, một lệnh chạy khiến Matthew chạy một mét trong khi nhảy đưa anh ta về phía trước chính xác bốn mét. Đối với ví dụ được đưa ra ở trên, chuyển động sau đây là có thể:

RRJRJRR

có vẻ như sau:

Minh họa của phong trào RRJRJRR

Nếu không có đường dẫn an toàn xuyên qua phong cảnh, thì !nên in một dấu chấm than ( ).

Đầu vào mẫu

--------
----__--___---
-_______
-_-_-_-_-_-
-

Đầu ra mẫu

JRRR
RRJRJRR
!
!

(đầu ra cuối cùng trống vì không cần di chuyển, nhưng tôi đoán, Markdown không thể phân tích cú pháp này)

chú thích

Chỉ có một đường dẫn khả dĩ duy nhất là cần thiết, vì vậy đầu ra chương trình không phải tuân thủ chính xác với đầu ra mẫu. Miễn là một giải pháp được đưa ra nếu nó tồn tại và mọi lệnh di chuyển di chuyển xuống đất và đồng hồ cuối cùng đạt được cuối cùng, đầu ra là hợp lệ.

Đầu ra bổ sung về lỗi tiêu chuẩn được bỏ qua.

Điều kiện chiến thắng

Mã ngắn nhất sẽ thắng, như thông lệ trong golf. Trong trường hợp hòa, giải pháp trước đó thắng.

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

Có hai tập lệnh kiểm tra, chứa các trường hợp kiểm thử giống hệt nhau:

Yêu cầu trong cả hai trường hợp : <test script> <my program> [arguments], ví dụ ./test ruby jumprun.rbhoặc ./test.ps1 ./jumprun.exe.

Một lưu ý khác

Nhiệm vụ này là một phần của cuộc thi golf được tổ chức tại trường đại học của tôi trong năm 2011-W24. Điểm số và ngôn ngữ của các thí sinh của chúng tôi như sau:

  • 104 - Haskell
  • 131 - Haskell
  • 154 - C
  • 170 - C
  • 275 - VB.NET
  • 286 - Lisp thông thường

Giải pháp của chúng tôi là

  •   92 - Ruby
  • 124 - PowerShell

@Joey Tôi gặp lỗi khi chạy test.sh với ./test.sh perl jump.pl- ./test.sh: line 42: syntax error near unexpected token 'done', trong bash 3.2.48
swilliams

@ Tôi đã xóa bộ nhớ cache, tải xuống và nó hoạt động rất tốt. Cảm ơn.
swilliams

Nhìn vào các giải pháp, nó rõ ràng là quá tầm thường. Lời xin lỗi.
Joey

1
Tôi cho rằng chạy ngược / nhảy không được phép? Nếu có, nó sẽ làm cho các cảnh quan như - - - có thể giải quyết được.
Keith Randall

Keith: một chút quá muộn bây giờ để thay đổi nhiệm vụ, tôi đoán.
Joey

Câu trả lời:


7

Perl, 53 ký tự

s/-...(?=(-|-...)*-$)/J/g;y/-/R/;/_/?$_="!":s/.$//

Chạy cái này với perl -p jumpnrun.pl. Tôi đã đếm 3 ký tự cho -ptùy chọn, đó là chênh lệch độ dài giữa perl jumpnrun.plperl -p jumpnrun.pl.

Tôi không rành về Perl, vì vậy tôi khá chắc chắn rằng điều này có thể rút ngắn hơn nữa. Điều này sử dụng một biểu thức chính tương tự như giải pháp của Howard .


3

Ruby, 93 90 79 70 ký tự

Tôi nghĩ rằng một giải pháp regex sẽ khá tốt và nhỏ gọn (hãy để công cụ đối sánh thực hiện công việc). Thật không may, tất cả các trường hợp cạnh và phương pháp điều trị đặc biệt đã khiến điều này kéo dài như vậy - ít nhất là tôi đã không chạm vào 100 ;-).

puts gets.gsub(/-...(?=(-|-...)*-$)/,?J).tr(?-,?R)=~/^([JR]*)R$/?$1:?!

Nó vượt qua tất cả các testcase của kịch bản được cung cấp.

Đã lưu một số ký tự so với tập lệnh trước đó (bây giờ một cuộc gọi đến gsublà đủ).

Chỉnh sửa 1: Thay đổi puts z!=?-??!:''thành z!=?-&&$><<?!sau khi kịch bản thử nghiệm cho phép không có đầu ra cho trường hợp thử nghiệm 1.

Chỉnh sửa 2: Phiên bản trước là

z=gets.chop
z.chars{z.sub!(/^(-|-...)((-|-...)*-)$/){$><<($1==?-??R:?J);$2}}
z!=?-&&$><<?!

Ý tưởng ban đầu của tôi là thay thế các nhân vật bằng cách sử dụng chiến lược nhìn phía sau và nhìn về phía trước như thế này: Mô hình là ^(?<=[RJ]*)(-|-...)(?=(-|-...)*-$)và sau đó tôi sẽ thay thế '-' bằng 'R' và ngược lại bằng 'J'. Thật không may, Ruby không cho phép nhìn phía sau có chiều dài thay đổi và một nhóm bắt giữ khác cho phần đầu tiên làm cho mã dài hơn.

Vì vậy, sau đó tôi đã thực hiện phương pháp lặp: nếu tôi có thể bắt đầu bằng một bước hoặc nhảy ^(-|-...)theo sau là một loạt các bước khác hoặc nhảy cho đến nền tảng cuối cùng (-|-...)*-$thì tôi in chữ cái tương ứng, xóa một / bốn ký tự đầu tiên và bắt đầu lại. Bật thậm chí có thể điều chỉnh mức ưu tiên của RJ so với JR bằng cách chuyển đổi các lựa chọn bên trong biểu thức (hiện tại nó thích RJ hơn).

Chỉnh sửa 3: Chia nhỏ bản phụ

puts (z=gets.chop.gsub(/(-...|-)(?=(-|-...)*-$)/){$1==?-??R:?J})=~/_/??!:z.chop

làm hai

puts (z=gets.chop.gsub(/-...(?=(-|-...)*-$)/,?J).tr(?-,?R))=~/_/??!:z.chop

đưa ra một vài ký tự. Cuối cùng tôi đã xoay sở để thoát khỏi vấn đề cuối dòng này nhưng với chi phí: việc phát hiện lỗi sẽ tốn thêm một số ký tự.


Bạn có thể lưu 3 ký tự bằng cách thay đổi dòng cuối cùng thành z!=?-&&$><<?!. Ngoài ra, giải pháp tuyệt vời, +1!
Ventero

@Ventero Tôi đã có một thử nghiệm đầu tiên thất bại vì không có đầu ra nào cho "-" ;-)
Howard

Hừm, có vẻ như tập lệnh PowerShell của tôi có một lỗi nhỏ. Rõ ràng là không chấp nhận đầu vào cho Thử nghiệm 2 và sẽ không chấp nhận nó cho Thử nghiệm 1. Điều đó thật ... kỳ lạ, phải nói là ít nhất. Tôi sẽ cố gắng sửa chữa.
Joey

Ok, tập lệnh kiểm tra nên được sửa và không còn từ chối một kết quả thực sự trống cho bài kiểm tra 1. Ok, bây giờ nó phải được sửa.
Joey

@Joey Danke. Nun sind es 90 ;-)
Howard

1

Perl - 71 60

$_=<>;y/-/R/;s/R...(?=(R(...)?)*R$)/J/g;print/_/?"!":s/.$//r

Bây giờ vượt qua tất cả các testcase. :) Hóa ra tôi đã loại bỏ nhân vật cuối cùng quá sớm ... và một nửa regex ban đầu của tôi là hoàn toàn dư thừa.

$ _ = $ ARGV [0]; y / - / R /; s / (R ... (? = R)) (R * (? = R)) / J $ 2 / g; chop; print / /? "!": $ , $ /

Một giải pháp regex khác, vượt qua 5 testcase trong bài.

Có thể rút ngắn bằng cách chạy dưới dạng một lớp lót -Esaythay vì print, nhưng sau đó perl cố gắng diễn giải đầu vào là một công tắc ... ( Unrecognized switch: -_-_-_-_-_-)


Câu hỏi nói rằng đầu vào được đưa ra trên stdin. Khi thay đổi giải pháp của bạn để đọc từ stdin thay vì sử dụng $ARGV, nó vẫn thất bại 108 testcase từ các kịch bản thử nghiệm.
Ventero

@Ventero Ôi trời ơi ... Tôi nghĩ tôi biết tại sao nó lại như vậy, tôi sẽ sớm khắc phục ... đó là những gì tôi nhận được khi không trải qua tất cả các thử nghiệm ...> _>
swilliams

Chà, ý định của các kịch bản là cho phép mọi người dễ dàng kiểm tra tính hợp lệ và tuân thủ các đặc điểm kỹ thuật :-)
Joey

@Joey Vấn đề là bằng cách nào đó tôi đã xoay sở để nhầm lẫn 'kịch bản thử nghiệm' với 'triển khai tham chiếu' cho đến khi Ventero đăng bình luận của mình :) ... hiện tại kịch bản gần như đã được sửa, mặc dù hiện tại chỉ thất bại 20, tất cả đều phủ định sai
swilliams

1

Con trăn - 89 93 97 93 ký tự

Chỉ vì.

import re;i=re.sub('...(?<!---)-','J',input()[1:]);print('!'if'_'in i else re.sub('-','R',i))

Chỉ thất bại mười trường hợp thử nghiệm bây giờ (có tính đến các trường hợp có nhiều giải pháp hợp lệ). Tôi sẽ sửa nó đầy đủ sau.


Mượn một trong những chế độ làm việc, nó kết thúc như

import re;i=re.sub('-...(?=(-|-...)*-$)','J',input());print('!'if'_'in i else re.sub('-','R',i))

Với 96 ký tự.


1
Chỉ vượt qua 728 trường hợp thử nghiệm. Tôi đặt các kịch bản thử nghiệm ở đó cho một lý do, thực sự.
Joey

@Joey: Có vẻ như tôi đã quên cắt bỏ nhân vật chính từ đầu vào. Tôi ngớ ngẩn quá. Bây giờ nó đã được sửa.
JAB

Vẫn chỉ vượt qua 766/849 testcase.
Ventero

1

Haskell, 90 ký tự:

Giải pháp đầu tiên của tôi - lâu dài, nhưng hoạt động trong thời gian tuyến tính, sử dụng lập trình động. :) 150 ký tự :

x!y="!"
q '-'=max
q c=(!)
s i=r where r=zipWith3 q i(0&'R')$3&'J';n&c="":replicate n"!"++map(c#)r
c#"!"="!"
c#s=c:s
main=interact$reverse.last.s.init

Giải pháp thứ hai - chậm hơn nhiều (thời gian theo cấp số nhân), nhưng ngắn hơn nhiều: 90 ký tự

s"-\n"=""
s('-':t)=max('R'#s t)$'J'#s(drop 3 t)
s _="!"
c#"!"="!"
c#s=c:s
main=interact s
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.