Phrases inverses

15

Le but de ce défi est de recevoir une entrée et une sortie qui entrent mais avec l'ordre des phrases inversé. Exemple d'entrée:

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

Exemple de sortie:

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

Comme vous pouvez le voir dans les exemples, votre programme doit gérer les points d'interrogation, les points d'exclamation et les points. Vous pouvez supposer que chaque phrase a une ponctuation et un espace avant la phrase suivante. Les espaces / sauts de ligne sont corrects, tant qu'ils sont lisibles. Le code le plus court gagne.

Bonne chance!

EDIT: Vous pouvez supposer que les phrases n'ont pas de guillemets ou de parenthèses, mais si vous faites en sorte que votre code soit capable de gérer les deux, alors vous obtenez -5 octets Exemple de sortie pour les parens / guillemets:

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

la source
Pouvons-nous supposer qu'il n'y aura pas de guillemets ou de parenthèses? Sinon, comment les traitons-nous?
BrainSteel
Vous avez apporté une modification au message en clarifiant cela.
Pouvez-vous donner un exemple de sortie attendue pour une phrase contenant des guillemets ou des parenthèses, s'il vous plaît?
mbomb007
6
Si une phrase a une ponctuation entre guillemets ou parens, comment devons-nous la traiter?
isaacg
2
@Scimonster Vous voulez dire "ie", etc., non? Oh, et veuillez modifier ma citation de scénario de test pour être:"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.
Pas que Charles

Réponses:

9

Julia, 45 42 octets - 5 bonus = 37

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

Cela crée une fonction anonyme qui accepte une chaîne en entrée et renvoie la chaîne avec ses phrases inversées. Cela gère correctement tout caractère spécial, bien que les guillemets doubles et les signes dollar doivent être échappés, sinon ce ne sont pas des chaînes valides dans Julia.

Non golfé + explication:

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

Exemples:

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."

Et si vous n'aimez pas regarder les guillemets échappés dans la sortie:

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.

Sauvegardé 3 octets sur l'expression régulière grâce à Martin Büttner! Auparavant , ce a utilisé un lookbehind: (?<=[.?!]).

Alex A.
la source
Je ne pense pas que cela se qualifie pour le bonus ...
Optimizer
@Optimizer: Comment ça ne marche pas? Il fonctionne comme prévu avec des parenthèses, des citations, etc., comme indiqué dans le message.
Alex A.
Pouvez-vous fournir un lien en ligne pour tester, avec l'exemple de la section bonus de la question.
Optimizer
@Optimizer: La seule façon d'exécuter une version récente de Julia en ligne nécessite une inscription et ne prend pas en charge les permaliens. Serait-il suffisant d'inclure simplement l'entrée et la sortie ici dans le message?
Alex A.
Bien sûr, je suppose ..
Optimizer
7

CJam, 23 22 octets

Je ne sais pas si cela est admissible au bonus ou non, mais voici la solution:

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

Expansion de code (peu obsolète) :

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

Essayez-le en ligne ici

Optimiseur
la source
Ah, vous avez fait ce post juste après l'avoir édité au début. Vous obtenez un bonus de -5 maintenant (juste pour le rendre un peu plus difficile) Donc, un bonus de -5 pour vous! 18 octets, wow,
5

J, 35 32

Il gère presque les entrées bonus, sauf que je dois échapper à des apostrophes simples, donc je suppose que cela ne compte pas. (Aussi, ma première soumission ici)

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

Usage:

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

Perl, 27/25

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

Ou depuis la ligne de commande:

$perl -nE'say reverse/ |[^.!?]*./g'
nutki
la source
Agréable! Vous pouvez obtenir le bonus de -5 perl -nE 'say reverse/ |[^.?!]*.\)?/g', ce qui porte votre nombre total à 23.
ThisSuitIsBlackNot
2

PHP, 60

echo join(' ',array_reverse(preg_split('/(?<=[?!.])/',$s)));
romaninsh
la source
Pouvez-vous utiliser l'expression rationnelle à la [?!.]\Kplace?
Martin Ender
De plus, cela n'ajoute-t-il pas d'espaces supplémentaires dans la chaîne à moins que vous n'incluiez l'espace dans le motif pour le séparer?
Martin Ender
@ MartinBüttner, non, je ne pourrai pas restaurer le signe approprié lors de la jonction des données, nous avons donc besoin de quelque chose qui ne consommera pas le personnage.
romaninsh
2

Bash + coreutils, 40 octets

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

Cela lit à partir de STDIN donc l'entrée peut être redirigée depuis un fichier, ou simplement acheminée, par exemple:

$ 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. 
$ 
Traumatisme numérique
la source
Est-ce que cela fonctionne vraiment pour les parenthèses dans le sens où cela (foo bar.)est échangé en tant qu'unité?
Martin Ender
@ MartinBüttner On dirait que la question a été modifiée, donc je ne peux plus réclamer le bonus :(
Digital Trauma
2

Pip , 25 octets

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

Après avoir ajouté un espace à la chaîne d'entrée, on trouve tous les indices de ., ?et !, ajouter 2 et utiliser les^@ opérateur split-at pour diviser la chaîne en phrases (chacune avec un espace de fin). Inversez la liste et elle sera imprimée automatiquement à la fin du programme. Voilà!

Exemple montrant les étapes du calcul principal avec entrée 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! 
DLosc
la source
Non, vous ne le faites pas :)
Optimizer
2

Rétine , 61 34 33 30 octets

Crédits à nutki pour avoir réduit cela de 24 octets.

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

<empty>représente une ligne vide. Cela suppose que cela #ne fait pas partie de l'entrée, mais si ce n'est pas légitime, je pourrais l'échanger contre tout autre personnage, y compris "(que je n'aurais besoin de gérer que pour le bonus) ou quelque chose d'imprimable. Vous pouvez exécuter le code comme ça dans un seul fichier si vous utilisez l' -sindicateur, ou vous pouvez placer chaque ligne dans un fichier séparé et les transmettre à Retina.

Inverser cela avec un seul remplacement d'expression régulière est possible, mais vraiment lourd. Même avec les groupes d'équilibrage .NET, j'avais besoin d'environ 90 octets, j'ai donc essayé de le faire en plusieurs étapes.

Dans la rétine, chaque paire de lignes est une étape de remplacement, où la première ligne est le motif et la deuxième ligne est le remplacement.

^
#

Cette étape prépare simplement la chaîne pour un traitement ultérieur. Il ajoute un #comme marqueur. Ce marqueur indique que tout ce qui se trouve devant lui a déjà été placé au bon endroit et que tout ce qu'il faut après doit encore être traité.

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

Cette étape permute les phrases, en déplaçant à plusieurs reprises la dernière phrase devant le #(qui avance dans la chaîne dans le processus). Le +`demande à Retina de répéter cette étape jusqu'à ce que la sortie cesse de changer. À titre d'exemple, voici comment foo. bar! blah?serait traitée l'entrée :

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

Et enfin, nous supprimons simplement le marqueur:

#
<empty>
Martin Ender
la source
Pourquoi ne pas simplement .+=> $0 #et répéter (.*?[.!?] )(.*#)=> $2$1?
nutki
@nutki Oh, c'est beaucoup mieux, merci. :)
Martin Ender
1

Java, 113

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

JavaScript (ES6) 47 45

Comme il est indiqué, il s'agit d'un simple exercice d'expression régulière. En 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!"))
 

edc65
la source
J'allais faire du javascript, mais tu m'as battu.
BobTheAwesome
Cela produit des espaces supplémentaires avant tout sauf la dernière phrase (à l'origine la première). Je ne sais pas si c'est OK, car la tâche n'est pas très bien définie.
nutki
@nutki oui, je suis d'accord. Corrigé
edc65
1

Python 2, 62

Ne va pas s'améliorer pour le bonus, car il ne vaut probablement pas le coût en octets.

import re
print' '.join(re.split('(?<=[?!.]).',input())[::-1])
mbomb007
la source
Cela ne donne pas droit au bonus. Regardez l'exemple de bonus dans la question
Optimizer
@Optimizer Regardez dans l'historique des questions. Au moment où j'ai mis à jour ma question pour ajouter le bonus, ma sortie correspondait à l'exemple. Rien n'indiquait que les parenthèses pouvaient être en dehors d'une période.
mbomb007
Je pense que l'intention n'était que depuis le début. Un exemple solide est venu plus tard cependant. Cela ne signifie pas que vous obtenez toujours le bonus :) (j'ai supprimé le mien aussi)
Optimizer
1

Matlab (93 octets)

y=[32 input('','s')];y=sortrows([cumsum(ismember(y,'?!.'),'reverse');y]',1)';disp(y(4:2:end))
  • Cela suppose que l'entrée ne contient pas d'espaces de début ou de fin
  • Utilise l'entrée et la sortie standard
  • Testé dans Matlab 2014b
Luis Mendo
la source
1

Rubis 41

Les autres réponses Ruby n'ont pas assez de WTF.

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

Cela fonctionne au moins dans Ruby 2. Si le commutateur aet Ffonctionne en 1.8.7, je suppose que vous pourriez laisser tomber $_=pour enregistrer trois caractères.

Inverse chaque ligne sur stdin et imprime sur stdout:

$ ruby foo.rb <<< "Hello. Hi. How are you? Good, you? fine, thanks."
fine, thanks. Good, you? How are you? Hi. Hello.
daniero
la source
Pourriez-vous s'il vous plaît expliquer la réponse.
Mhmd
1

Ruby, 48 (42 sans les put) octets

reverse_sentence.rb

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

Usage:

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

Production:

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

La critique est plus que bienvenue.

DickieBoy
la source
2
Critique: vous avez mal orthographié «phrase».
Alex A.
enregistrer 6 caractères: .join(" ")=>*" "
daniero
@AlexA. La meilleure rétroaction jamais!
DickieBoy
@daniero merci, bon à savoir
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."
tmartin
la source
0

C # - LINQPAD - 93 - 5 = 88 octets

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

Application console C # 189-5 = 184 octets

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

regex sans vergogne fouetté d'Alex A. :)

jzm
la source
Vous pouvez économiser 7 octets en plaçant votre application namespace Systemdans ce using Linq;usingText.RegularExpressions2x sauvegarde system.
ldam
Je ne pense pas que cela donne droit au bonus. Regardez l'exemple de bonus dans la question
Optimizer
0

Clojure - 44 71 caractères

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

RE amélioré et simplifié, éliminé les espaces inutiles.

La sortie est une séquence de phrases dans la chaîne d'origine, avec l'ordre des phrases inversé:

Entrée: "Bonjour ami. Que fais-tu? Je parie que c'est quelque chose que je veux faire aussi!" Sortie: ("Je parie que c'est quelque chose que je veux faire aussi!" "Que faites-vous?" "Bonjour ami.")

Bob Jarvis - Réintégrer Monica
la source
0

Rubis, 47

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

crédits à Martin Büttner , pour avoir sauvé certains personnages.

Mhmd
la source
1
Vous pouvez lire l'entrée de STDIN avec getspour enregistrer un octet, l'imprimer avec $><<pour enregistrer l'octet (pas besoin d'espace) et joindre la chaîne avec *''pour enregistrer deux octets.
Martin Ender
@ MartinBüttner merci pour la suggestion, je n'irais pas avec la lecture de l'entrée de STDIN, cependant. Tout simplement parce qu'il y aura une nouvelle ligne de fuite.
Mhmd
En fait, je pense que votre code se traduira actuellement par un espace de premier plan.
Martin Ender
mmm, vous avez raison. Je verrai ce que je dois faire.
Mhmd
0

CJam, 21 octets

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

Cela fonctionne en transformant les espaces après !s, .s et ?s en nombre 1 (pas le caractère 1 ni le caractère avec le point de code 1, de sorte que l'entrée peut toujours les contenir), en divisant par 1, en inversant l'ordre des morceaux résultants et en joignant par des espaces.

Essayez-le en ligne dans l' interpréteur CJam .

Comment ça fonctionne

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)
Dennis
la source