Câu ngược


15

Mục tiêu của thử thách này là nhận đầu vào và đầu ra đầu vào đó nhưng với thứ tự câu bị đảo ngược. Ví dụ đầu vào:

Hello friend. What are you doing? I bet it is something I want to do too!

Kết quả ví dụ:

I bet it is something I want to do too! What are you doing? Hello friend.

Như bạn có thể nói từ các ví dụ, chương trình của bạn phải xử lý các dấu hỏi, dấu chấm than và dấu chấm. Bạn có thể giả sử mỗi câu có dấu câu và hơn khoảng trắng trước câu tiếp theo. Trailing space / newlines là ok, miễn là nó có thể đọc được. Mã ngắn nhất sẽ thắng.

Chúc may mắn!

EDIT: Bạn có thể giả sử các câu không có dấu ngoặc kép hoặc dấu ngoặc đơn, nhưng nếu bạn tạo mã của mình có thể xử lý cả hai câu đó thì bạn nhận được -5 byte Kết quả đầu ra cho parens / ngoặc kép:

"Hello, " she said. (I didn't know what she was talking about.) --> (I didn't know what she was talking about.) "Hello, " she said.

Chúng ta có thể cho rằng sẽ không có bất kỳ trích dẫn hay dấu ngoặc đơn nào không? Nếu không, làm thế nào để chúng ta xử lý chúng?
BrainSteel

Thực hiện một chỉnh sửa để xóa bài đăng lên.

Bạn có thể đưa ra một ví dụ về đầu ra dự kiến ​​cho một câu có chứa dấu ngoặc kép hoặc parens không?
mbomb007

6
Nếu một câu có dấu câu trong dấu ngoặc kép hoặc dấu ngoặc, chúng ta nên xử lý như thế nào?
isaacg

2
@Scimonster Ý bạn là "tức là", v.v., phải không? Ồ, và vui lòng sửa đổi trích dẫn trường hợp thử nghiệm của tôi thành:"Hello!" she said. (I hesitated. How should I respond? This is too much!) I responded, "Hi there. How are you? What is your cat's name?" without thinking any more about it.
Không phải Charles

Câu trả lời:


9

Julia, 45 42 byte - 5 tiền thưởng = 37

s->join(reverse(split(s,r"[.?!]\K "))," ")

Điều này tạo ra một hàm ẩn danh chấp nhận một chuỗi làm đầu vào và trả về chuỗi với các câu bị đảo ngược. Điều này xử lý bất kỳ ký tự đặc biệt nào một cách thích hợp, mặc dù dấu ngoặc kép và ký hiệu đô la phải được thoát, nếu không chúng không phải là chuỗi hợp lệ trong Julia.

Ungolfed + giải thích:

function f(s)
    # Get individual sentences by splitting on the spaces that
    # separate them. Spaces are identified by matching punctuation
    # then moving the position beyond that match and matching a
    # space. This is accomplished using \K.

    sentences = split(s, r"[.?!]\K ")

    # Reverse the order of the array of sentences.

    reversed_order = reverse(sentences)

    # Join the array elements into a string, separated by a space.

    join(reversed_order, " ")
end

Ví dụ:

julia> f("Hello friend. What are you doing? I bet it is something I want to do too!")
"I bet it is something I want to do too! What are you doing? Hello friend."

julia> f("\"Hello, \" she said. (I didn't know what she was talking about.)")
"(I didn't know what she was talking about.) \"Hello, \" she said."

Và nếu bạn không thích nhìn vào các trích dẫn đã thoát trong đầu ra:

julia> println(f("\"Hello, \" she said. (I didn't know what she was talking about.)"))
(I didn't know what she was talking about.) "Hello, " she said.

Đã lưu 3 byte trên biểu thức thông thường nhờ Martin Büttner! Trước đây điều này đã sử dụng một cái nhìn:(?<=[.?!]) .


Tôi không nghĩ rằng điều này đủ điều kiện nhận tiền thưởng ...
Trình tối ưu hóa

@Optimizer: Làm sao không? Nó hoạt động như mong đợi với dấu ngoặc đơn, dấu ngoặc kép, vv như được đưa ra trong bài.
Alex A.

Bạn có thể cung cấp một liên kết trực tuyến để kiểm tra, với ví dụ từ phần thưởng của câu hỏi.
Trình tối ưu hóa

@Optimizer: Cách duy nhất để chạy phiên bản Julia trực tuyến gần đây yêu cầu đăng ký và không hỗ trợ permalinks. Nó có đủ để chỉ đơn giản bao gồm đầu vào và đầu ra ở đây trong bài viết?
Alex A.

Chắc chắn, tôi đoán ..
Trình tối ưu hóa

7

CJam, 23 22 byte

Tôi không chắc điều này có đủ điều kiện nhận thưởng hay không, nhưng đây là giải pháp:

Sq{1$".?!"-{])[}|}%]W%

Mở rộng mã (bit lỗi thời) :

Sq+                      e# Read the input and prepend with a space
   {            }%       e# For each input character
    _".?!"&              e# Copy and check if its one of ., ? and !
           {][}&         e# If it is one of the above, wrap everything till now in an array
                         e# and start a new array to be wrapped next time we get one of those
                         e# three characters. We now have an array of strings, each having
                         e# a single sentence
                  W%     e# Reverse the ordering of these sentences
                    s(   e# Convert to string and remove the first space

Dùng thử trực tuyến tại đây


Ah, bạn đã thực hiện bài đăng này ngay sau khi tôi chỉnh sửa nó lúc đầu. Bạn nhận được -5 phần thưởng ngay bây giờ (Chỉ để làm cho nó khó hơn một chút) Vì vậy, -5 phần thưởng cho bạn! 18 byte, wow, không chắc là có thể đánh bại được không: P

5

J, 35 32

Nó gần như xử lý đầu vào tiền thưởng, ngoại trừ tôi phải thoát các dấu nháy đơn, vì vậy tôi đoán nó không được tính. (Ngoài ra, lần gửi đầu tiên của tôi ở đây)

f=.;@|.@(]<;.2~'.?!'e.~])@,~&' '

Sử dụng:

f 'Hello friend. What are you doing? I bet it is something I want to do too!'

4

Perl, 27/11

#!perl -n
print reverse/ |[^.!?]*./g

Hoặc từ dòng lệnh:

$perl -nE'say reverse/ |[^.!?]*./g'

Đẹp! Bạn có thể nhận được phần thưởng -5 với perl -nE 'say reverse/ |[^.?!]*.\)?/g', nâng tổng số của bạn lên 23.
ThisSuitIsBlackNot

2

PHP, 60

echo join(' ',array_reverse(preg_split('/(?<=[?!.])/',$s)));

Bạn có thể sử dụng regex [?!.]\Kthay thế?
Martin Ender

Ngoài ra, điều này không thêm các khoảng trắng bổ sung vào chuỗi trừ khi bạn bao gồm khoảng trắng trong mẫu để phân chia?
Martin Ender

@ MartinBüttner, không, tôi sẽ không thể khôi phục lại dấu hiệu thích hợp khi nối lại dữ liệu, vì vậy chúng tôi cần thứ gì đó sẽ không tiêu thụ ký tự.
romaninsh

2

Bash + coreutils, 40 byte

sed 's/\([?.!]\) */\1\n/g'|tac|tr \\n \ 

Điều này đọc từ STDIN để đầu vào tôi có thể chuyển hướng từ một tệp, hoặc đơn giản là được dẫn vào, ví dụ:

$ printf 'Hello friend. What are you doing? I bet it is something I want to do too!' | sed 's/\([?.!]\) */\1\n/g'|tac|tr \\n \ 
I bet it is something I want to do too! What are you doing? Hello friend. 
$ 

Điều này thực sự làm việc cho dấu ngoặc đơn theo nghĩa, (foo bar.)được hoán đổi như một đơn vị?
Martin Ender

@ MartinBüttner Có vẻ như câu hỏi đã được chỉnh sửa, vì vậy tôi không còn có thể nhận phần thưởng :(
Chấn thương kỹ thuật số

2

Pip , 25 byte

a.:sRV(a^@2+$ALa@*^".?!")

Sau khi gắn thêm một không gian để các chuỗi đầu vào, chúng ta thấy tất cả các chỉ số của ., ?!, thêm 2, và sử dụng^@ toán tử split-at để chia chuỗi thành các câu (mỗi chuỗi có một khoảng trắng ở cuối). Đảo ngược danh sách và nó được in tự động vào cuối chương trình. Võngà!

Ví dụ hiển thị các giai đoạn tính toán chính với đầu vào A! B? C. D!:

              ^".?!"     ["." "?" "!"]
           a@*           [[7] [4] [1 10]]
        $AL              [7 4 1 10]
      2+                 [9 6 3 12]
   a^@                   ["A! " "B? " "C. " "D! "]
RV(                 )    ["D! " "C. " "B? " "A! "]

                         D! C. B? A! 

Không có bạn không :)
Trình tối ưu hóa

2

Võng mạc , 61 34 33 30 byte

Tín dụng cho nutki để cắt giảm 24 byte.

^
#
+`(#.*[.!?]) (.+)
$2 $1
#
<empty>

Nơi <empty>viết tắt của một dòng trống. Điều này giả định rằng đó #không phải là một phần của đầu vào, nhưng nếu điều đó không hợp pháp, tôi có thể trao đổi nó cho bất kỳ nhân vật nào khác, bao gồm "(mà tôi chỉ cần xử lý phần thưởng) hoặc một cái gì đó không thể in được. Bạn có thể chạy mã như thế trong một tệp duy nhất nếu bạn sử dụng -scờ hoặc bạn có thể đặt từng dòng trong một tệp riêng biệt và chuyển tất cả chúng cho Retina.

Có thể đảo ngược điều này với một sự thay thế regex duy nhất, nhưng thực sự cồng kềnh. Ngay cả với các nhóm cân bằng .NET tôi cũng cần khoảng 90 byte, vì vậy thay vào đó tôi đã thử thực hiện theo nhiều bước.

Trong Retina, mỗi cặp dòng là một giai đoạn thay thế, trong đó dòng đầu tiên là mẫu và dòng thứ hai là thay thế.

^
#

Giai đoạn này chỉ đơn giản là chuẩn bị chuỗi để xử lý thêm. Nó chuẩn bị #một điểm đánh dấu. Điểm đánh dấu này chỉ ra rằng mọi thứ ở phía trước của nó đã được đặt đúng chỗ và mọi thứ sau đó vẫn cần được xử lý.

+`(#.*[.!?]) (.+)
$2 $1

Giai đoạn này hoán đổi các câu, bằng cách liên tục di chuyển câu cuối cùng trước #(di chuyển về phía trước qua chuỗi trong quy trình). Các +`chỉ thị Retina để lặp lại giai đoạn này cho đến khi đầu ra ngừng thay đổi. Ví dụ, đây là cách foo. bar! blah?xử lý đầu vào :

#foo. bar! blah?
blah? #foo. bar!
blah? bar! #foo.

Và cuối cùng chúng ta chỉ cần xóa điểm đánh dấu:

#
<empty>

Tại sao không chỉ .+=> $0 #và lặp lại (.*?[.!?] )(.*#)=> $2$1?
nutki

@nutki ơi, đẹp hơn nhiều, cảm ơn bạn. :)
Martin Ender

1

Java, 113

s->{String t[]=s.split("(?<=[\\.?!]) "),u="";for(int i=t.length;i-->0;)u+=t[i]+" ";return u.replaceAll(".$","");}

1

JavaScript (ES6) 47 45

Như đã nói, đó là một bài tập regex đơn giản. Trong javascript:

// ES6 - FireFox only
F=t=>t.match(/\S[^.!?]+./g).reverse().join(' ')

// ES5 - so much longer
function G(t){return t.match(/\S[^.!?]+./g).reverse().join(' ')}

// TEST

alert(G("Hello friend. What are you doing? I bet it is something I want to do too!"))
 


Tôi sẽ làm javascript, nhưng bạn đã đánh bại tôi.
BobTheAwgie

Điều này tạo ra khoảng trắng thừa trước tất cả trừ câu cuối cùng (ban đầu là câu đầu tiên). Không chắc chắn nếu nó ổn, vì nhiệm vụ không được xác định rõ.
nutki

@nutki vâng, tôi đồng ý. Cố định
edc65

1

Con trăn 2, 62

Sẽ không cải thiện phần thưởng, vì có lẽ nó không xứng đáng với chi phí byte.

import re
print' '.join(re.split('(?<=[?!.]).',input())[::-1])

Điều này không đủ điều kiện cho tiền thưởng. Nhìn vào ví dụ tiền thưởng trong câu hỏi
Trình tối ưu hóa

@Optimizer Hãy nhìn vào lịch sử câu hỏi. Tại thời điểm tôi cập nhật câu hỏi của mình để thêm phần thưởng, đầu ra của tôi khớp với ví dụ. Không có gì chỉ ra rằng dấu ngoặc đơn có thể nằm ngoài một khoảng thời gian.
mbomb007

Tôi nghĩ rằng ý định này chỉ là từ đầu. Một ví dụ vững chắc đến sau mặc dù. Không có nghĩa là bạn vẫn nhận được tiền thưởng :) (Tôi cũng đã xóa phần thưởng của mình)
Trình tối ưu hóa

1

Matlab (93 byte)

y=[32 input('','s')];y=sortrows([cumsum(ismember(y,'?!.'),'reverse');y]',1)';disp(y(4:2:end))
  • Điều này giả sử đầu vào không chứa khoảng trắng ở đầu hoặc cuối
  • Sử dụng đầu vào và đầu ra tiêu chuẩn
  • Đã thử nghiệm trong Matlab 2014b

1

Ruby 41

Các câu trả lời khác của Ruby không có đủ WTF.

#!ruby -apF(?<=[.!?])\s
$_=$F.reverse*" "

Điều này ít nhất hoạt động trong Ruby 2. Nếu aFcông tắc hoạt động trong 1.8.7, tôi đoán bạn có thể thả $_=để lưu ba ký tự.

Đảo ngược mọi dòng trên stdin và in ra thiết bị xuất chuẩn:

$ ruby foo.rb <<< "Hello. Hi. How are you? Good, you? fine, thanks."
fine, thanks. Good, you? How are you? Hi. Hello.

Bạn có thể vui lòng giải thích câu trả lời.
Mhmd

1

Ruby, 48 (42 mà không đặt) byte

Reverse_sentence.rb

puts $*[0].scan(/\S[^.!?]+./).reverse.join(" ")

Sử dụng:

ruby reverse_sentence.rb 'Hello friend. What are you doing? I bet it is something I want to do too!'

Đầu ra:

I bet it is something I want to do too! What are you doing? Hello friend.

Criticism more than welcome.


2
Criticism: You spelled "sentence" incorrectly.
Alex A.

save 6 characters: .join(" ") => *" "
daniero

@AlexA. Best feedback ever!
DickieBoy

@daniero thanks, nice to know
DickieBoy

1

k, 31

{1_,/|(0,1+&x in"?!.")_x:" ",x}

.

k){1_,/|(0,1+&x in"?!.")_x:" ",x} "Hello friend. What are you doing? I bet it is something I want to do too!"
"I bet it is something I want to do too! What are you doing? Hello friend."

0

C# - LINQPAD - 93 - 5 = 88 bytes

void Main(){string.Join(" ",Regex.Split(Console.ReadLine(),"(?<=[.?!]) ").Reverse()).Dump();}

C# Console App 189 - 5 = 184 bytes

using System;using System.Linq;using System.Text.RegularExpressions;class P{static void Main(){Console.WriteLine(string.Join(" ",Regex.Split(Console.ReadLine(), "(?<=[.?!]) ").Reverse()));}}

regex shamelessly flogged from Alex A. :)


You can save 7 bytes by putting your application in namespace System then within that using Linq;usingText.RegularExpressions saving 2x system.
ldam

I don't think that this qualifies for the bonus. Look at the bonus example in the question
Optimizer

0

Clojure - 44 71 chars

(defn rs[s](reverse(re-seq #"\S.+?[.!?]"s)))

Improved and simplified RE, eliminated unnecessary whitespace.

Output is a sequence of the sentences in the original string, with the order of the sentences reversed:

Input: "Hello friend. What are you doing? I bet it is something I want to do too!" Output: ("I bet it is something I want to do too!" "What are you doing?" "Hello friend.")


0

Ruby, 47

$><<gets.strip.split(/(?<=[.?!]) /).reverse*' '

credits to Martin Büttner, for saving some characters.


1
You can read the input from STDIN with gets to save a byte, print it with $><< to save byte (no need for a space) and join the string with *'' to save two bytes.
Martin Ender

@MartinBüttner thanks for the suggestion, I wouldn't go with reading from the input from STDIN, though. Simply because there will be a trailing new line.
Mhmd

Actually, I think your code will currently result in a leading space.
Martin Ender

mmm, you're right. I'll see what should I do.
Mhmd

0

CJam, 21 bytes

1q{1?_"!.?"-}%1a/W%S*

This works by turning spaces after !s, .s and ?s into the number 1 (not the character 1 nor the character with code point 1, so the input can still contain those), splitting at 1's, reversing the order of the resulting chunks and joining by spaces.

Try it online in the CJam interpreter.

How it works

1                     e# B := 1
 q                    e# Q := input()
  {         }%        e# for each C in Q (map):
   1?                 e#   C := B ? C : 1
     _"!.?"-          e#   B := string(C).strip("!.?")
              1a/     e# Q := Q.split([1])
                 W%   e# Q := reverse(Q)
                   S* e# Q := Q.join(" ")
                      e# print(Q)
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.