Entschlüsseln Sie diese case- (sehr) sensiblen Strings

53

Tor

Dies ist eine einfache Herausforderung. Ihr Ziel ist es, eine Zeichenfolge zu entschlüsseln, indem Sie jeden Buchstaben mit dem nächsten Buchstaben derselben Groß- / Kleinschreibung vertauschen, während Sie Nicht-Buchstaben-Zeichen unverändert lassen.

Beispiel

Schritt für Schritt Erklärung

  1. Das erste Zeichen ist a E. Wir suchen nach dem nächsten Buchstaben in Großbuchstaben: a C. Wir tauschen diese Zeichen aus, was zu führt CdoE!.

  2. Wir rücken zum nächsten Zeichen vor: Dies ist ein d. Wir suchen den nächsten Buchstaben in Kleinbuchstaben: a o. Wir tauschen diese Zeichen aus, was zu führt CodE!.

  3. Wir rücken zum nächsten Charakter vor: Dies ist der d, den wir gerade hierher gezogen sind. Wir ignorieren es, weil es bereits verarbeitet wurde.

  4. Wir gehen zum nächsten Zeichen über: Dies ist das Zeichen E, das hier in Schritt 1 verschoben wurde. Wir ignorieren es, weil es bereits verarbeitet wurde.

  5. Wir rücken zum nächsten Zeichen vor: Dies ist ein !. Wir ignorieren es, weil es kein Brief ist.

Regeln

  • Sie können davon ausgehen, dass die Eingabezeichenfolge ausschließlich aus druckbaren ASCII-Zeichen im Bereich von 32 bis 126 besteht.

  • Sie können entweder ein vollständiges Programm oder eine Funktion schreiben, die das Ergebnis entweder ausgibt oder zurückgibt.

  • Wenn die Eingabezeichenfolge eine ungerade Anzahl von Buchstaben enthält, kann der letzte verbleibende Buchstabe nicht mit einem anderen ausgetauscht werden und sollte an Ort und Stelle bleiben, unabhängig von der jeweiligen Schreibweise. Dieselbe Logik gilt, wenn die Zeichenfolge eine gerade Anzahl von Buchstaben enthält, jedoch eine ungerade Anzahl von Großbuchstaben und eine ungerade Anzahl von Kleinbuchstaben.

  • Das ist Code-Golf, also gewinnt die kürzeste Antwort in Bytes. Standardlücken sind verboten.

Testfälle

Input : lLEhW OroLd!
Output: hELlO WorLd!

Input : rpGOZmaimgn uplRzse naC DEoO LdGf
Output: prOGRamming puzZles anD COdE GoLf

Input : eIt uqHKC RBWOO xNf ujPMO SzRE HTL EOvd yAg
Output: tHe quICK BROWN fOx juMPS OvER THE LAzy dOg

Input : NraWgCi: Nsas-eNEiTIsev rNsiTG!!
Output: WarNiNg: Case-sENsITive sTriNG!!

Nicht so zufällige Testfälle:

Input : (^_^)
Output: (^_^)

Input : AWCTY HUOS RETP
Output: WATCH YOUR STEP

Input : hwn oeesd acsp nawyya
Output: who needs caps anyway

Input : SpMycaeIesKyBorekn
Output: MySpaceKeyIsBroken

Input : D's mroyr, Ivam. I'e faardi I act'n od htta.
Output: I'm sorry, Dave. I'm afraid I can't do that.
Arnauld
quelle
Ich gehe davon aus, dass ein ähnlicher Kommentar gilt, wenn die Eingabe eine gerade Anzahl von Buchstaben, aber eine ungerade Anzahl von Großbuchstaben und eine ungerade Anzahl von Kleinbuchstaben enthält.
Greg Martin
14
Dies ist eine wirklich clevere Herausforderung ... Ich mag auch die Tatsache, dass Testfälle durch Eingeben eines Kleinbuchstabens, zufälliges Ändern einiger Buchstaben in Großbuchstaben und anschließendes Ausführen des gleichen Programms, das das Problem löst, erstellt werden können!
Greg Martin
1
@ GregMartin Ich fand heraus, dass das Problem sein eigenes Gegenteil ist, weil ich beim Versuch eines Testfalls versehentlich die Ausgabe anstelle der Eingabe eingegeben habe :-)
Luis Mendo
Ich denke, Sie sollten Testfälle mit mehr als einem Nicht-Buchstaben-ASCII-Zeichen einschließen ... Ich denke, einige Implementierungen könnten sie versehentlich gegeneinander austauschen, wenn dies nicht der Fall sein sollte.
Greg Martin
3
Die Testfälle sollten wahrscheinlich eine Zeichenfolge ohne Großbuchstaben und eine Zeichenfolge ohne Buchstaben enthalten.
Dennis

Antworten:

4

Jelly , 21 20 19 18 Bytes

s2UF,
nŒlTÇyJịŒsµ⁺

Probieren Sie es online!

Wie es funktioniert

nŒlTÇyJịŒsµ⁺  Main link. Argument: s (string)

 Œl           Convert to lowercase.
n             Test for inequality.
   T          Truth; yield all indices of 1's.
    Ç         Call the helper link. Yields [A, B] (pair of lists).
      J       Indices; yield I := [1, ..., len(s)].
     y        Translate; replace the integers of I that occur in A with the
              corresponding integers in B.
        Œs    Swapcase; yield s with swapped case.
       ị      Use the translated index list to index into s with swapped case.
          µ   Combine all links to the left into a chain.
           ⁺   Duplicate the chain, executing it twice.


s2UF,         Helper link. Argument: J (list of indices)

s2            Split J into pairs. If the length is odd, the last list will be
              a singleton list.
  U           Upend; reverse each pair. This is a no-op for singletons lists.
   F          Flatten, concatenating the pairs.
    ,          Pair the previous result with J.
Dennis
quelle
18

Netzhaut , 53 Bytes

Nicht wirklich clever, aber eine saubere und gut lesbare Lösung

([a-z])(.*?)([a-z])
$3$2$1
([A-Z])(.*?)([A-Z])
$3$2$1

Probieren Sie es online!

Löwe
quelle
9

MATL , 22 Bytes

2:"tttk<f2etAZ))P5M(Yo

Probieren Sie es online! Oder überprüfen Sie alle Testfälle .

Wie es funktioniert

2:"       % Do the following twice
  ttt     %   Input string (implicit). Push three more copies
  k       %   Convert to lowercase
  <f      %   Indices of characters that had their code point increased by
          %   the lowercase conversion, i.e. that were uppercase letters
  2e      %   Convert to 2-row matrix. This pads a zero in the lower-right 
          %   corner if necessary
  tAZ)    %   Keep only columns that don't contain zeros. Thus if there
          %   was a character that can't be swapped it will be ignored             
  )       %   Get 2-row matrix of characters at those positions
  P       %   Flip vertically. This does the swapping
  5M      %   Push matrix of original indices again
  (       %   Write the swapped characters onto their original positions
  Yo      %   Change case. In the first iteration, this prepares the
          %   string so the second iteration will process the letters that
          %   were originally lowercase. In the second iteration, it
          %   undoes the change of case 
          % End (implicit)
          % Display (implicit)
Luis Mendo
quelle
6

Bash + Unix-Dienstprogramme, 77 62 57 56 54 Byte

sed -r "s/([$1)([^$1*)([$1)/\3\2\1/g"||$0 a-z]|$0 A-Z]

Eingabe in stdin. Ausgabe in Standardausgabe.

(In dieser letzten Version wird stderr auch geschrieben, aber PPCG-Konsens scheint zu sein, dass das in Ordnung ist - stderr wird einfach ignoriert. )

Edit 1: Danke an @Dennis für 15 Bytes! Verbesserungen: (a) Eingabe über stdin; (b) Kombinieren von 2 sed-Skripten zu einem; und (c) Ersetzen von tr durch Ersetzen durch Bash-Parameter-Erweiterung; (b) und (c) sind in Edit 2 verschwunden.

Edit 2: 5 zusätzliche Bytes kürzer. Verwendete einen Funktionsaufruf, um sowohl (b) als auch (c) in Edit 1 zu ersetzen.

Edit 3: Ein weiteres Byte übergeben] als Teil der Funktionsargumente.

Edit 4: Ersetzt die beiden Funktionsaufrufe durch Aufrufe des Programms selbst, wenn es keine Argumente enthält.

Testbed und Beispielausgabe:

for x in 'lLEhW OroLd!' 'rpGOZmaimgn uplRzse naC DEoO LdGf' 'eIt uqHKC RBWOO xNf ujPMO SzRE HTL EOvd yAg' 'NraWgCi: Nsas-eNEiTIsev rNsiTG!!' '(^_^)' 'AWCTY HUOS RETP' 'hwn oeesd acsp nawyya' 'SpMycaeIesKyBorekn' "D's mroyr, Ivam. I'e faardi I act'n od htta."; do ./swapping <<<"$x" 2>/dev/null; done

hELlO WorLd!
prOGRamming puzZles anD COdE GoLf
tHe quICK BROWN fOx juMPS OvER THE LAzy dOg
WarNiNg: Case-sENsITive sTriNG!!
(^_^)
WATCH YOUR STEP
who needs caps anyway
MySpaceKeyIsBroken
I'm sorry, Dave. I'm afraid I can't do that.
Mitchell Spector
quelle
6

ES6, 185 95 Bytes

i=>(o=[...i]).map((c,j)=>/[a-z]/i.test(c)?o[e=c>"Z"]=1/(b=o[e])?o[o[j]=o[b],b]=c:j:0)&&o.join``

Lösung mit Hilfe von @Neil, @Arnauld und @ edc65 stark verkürzt

Erläuterung

f = i =>
  // Get array of characters from input string
  (o = [...i])
    .map((c, j) => 
      // Check if it's a text character, otherwise skip it
      /[a-z]/i.test(c) ? 
        // Get last character position for case
        // merged with setting a variable for if the character is lowercase
        // merged with storing the current case character position,  
        // under properties on the array (with keys "true" or "false")
        o[e = c>"Z"] =
          // Check if there exists a character position to switch with
          // merged with storing the current position for quick access
          1/(b=o[e]) ? 
            // This statement will end up returning the Array subset, 
            // which will be falsy in the above conditional since (1/[])==false
            o[
              // Switch left character to the right
              o[j]=o[b]
            // Switch right character to the left
            ,b]=c : 
            // No character exists for case, so return current character position
            j
         // It was not a text character, so do nothing
         :0
      )
  // Join array and return as result
  && o.join``;

`lLEhW OroLd!
NraWgCi: Nsas-eNEiTIsev rNsiTG!!
rpGOZmaimgn uplRzse naC DEoO LdGf
eIt uqHKC RBWOO xNf ujPMO SzRE HTL EOvd yAg
(^_^)
AWCTY HUOS RETP
hwn oeesd acsp nawyya
SpMycaeIesKyBorekn
D's mroyr, Ivam. I'e faardi I act'n od htta`
  .split`\n`
  .map(testCase => console.log(f(testCase)));

Jan
quelle
6 Bytes, die umschließenden Parens sind überflüssig, wenn wir die zweite Anweisung entfernen :) Schön.
Jan
2
Bitte ignoriere meinen letzten Kommentar. Hier ist die 99:/[a-z]/i.test(c)?o[e=c>"Z"]=1/(b=o[e])?[o[b],o[j]]=[c,o[b]]:j:0
Arnauld
2
[o[b],o[j]]=[c,o[b]]könnte seino[o[j]=o[b],b]=c
edc65
Der wahre Meisterstrich hier ist die Verwendung von true und false als Indizes für ein Array
edc65
Danke Jungs, jetzt bis 95. Es wird immer schwieriger, die Lösung auf sinnvolle Weise zu dokumentieren. XD @ edc65 Sie werden als Eigenschaften für das Array-Objekt und nicht als Indizes gespeichert. Ja, Arnauld hat herausgefunden, dass sie auf dem Character Array gespeichert sind, aber die Wiederverwendung des Objekts war eher ein glücklicher Zufall, denke ich, der von einem separaten Vorschlag herrührte. Ursprünglich wurde es auf einem separaten Objekt gespeichert, was für den Umfang der Herausforderung natürlich völlig unnötig war.
Jan
3

Python , 82 Bytes

lambda s:S(r.lower(),t,S(r,t,s))
import re
S=re.sub
r='([A-Z])(.*?)'*2
t=r'\3\2\1'

Probieren Sie es online!

Dennis
quelle
wie funktioniert es? heißt der Lambda überhaupt?
Sarge Borsch
Das Lambda ist die tatsächliche (Funktions-) Vorlage. Alles andere ist nur Begleitcode, der ausgeführt werden muss, bevor das Lambda aufgerufen wird.
Dennis
3

QBasic, 229 Bytes

LINE INPUT s$
FOR i=1TO LEN(s$)
c$=MID$(s$,i,1)
IF"@"<c$AND"[">c$THEN
IF u THEN MID$(s$,u,1)=c$:MID$(s$,i,1)=u$
u=-i*(u=0)
u$=c$
ELSEIF"`"<c$AND"{">c$THEN
IF l THEN MID$(s$,l,1)=c$:MID$(s$,i,1)=l$
l=-i*(l=0)
l$=c$
END IF
NEXT
?s$

Strategie

Wir durchlaufen die Eingabezeichenfolge. Wenn wir auf einen Großbuchstaben stoßen, speichern wir ihn und seine Position. Wenn wir zum zweiten Mal auf einen Großbuchstaben stoßen, verwenden wir diese gespeicherten Werte, um ihn gegen den vorherigen auszutauschen. Gleiches gilt für Kleinbuchstaben.

(Ich wollte gerade eine längere Version veröffentlichen, in der ein Array verwendet wurde, da ich dachte, dass QBasic-Strings unveränderlich sind. Dann bin ich auf die Tatsache gestoßen, dass MID$(strng$, index, length) = replacement$alles gut funktioniert. Lebe und lerne.)

Ungolfed + kommentiert

LINE INPUT text$

FOR i = 1 TO LEN(text$)
  char$ = MID$(text$, i, 1)
  IF "A" <= char$ AND "Z" >= char$ THEN
    ' Uppercase
    IF upperIndex = 0 THEN
      ' This is the first of a pair of uppercase letters
      ' Store the letter and its index for later
      upperLetter$ = char$
      upperIndex = i
    ELSE
      ' This is the second of a pair of uppercase letters
      ' Put it at the position of the previous uppercase letter
      ' and put that letter at this letter's position
      MID$(text$, upperIndex, 1) = char$
      MID$(text$, i, 1) = upperLetter$
      upperIndex = 0
    END IF
  ELSEIF "a" <= char$ AND "z" >= char$ THEN
    ' Lowercase
    IF lowerIndex = 0 THEN
      ' This is the first of a pair of lowercase letters
      ' Store the letter and its index for later
      lowerLetter$ = char$
      lowerIndex = i
    ELSE
      ' This is the second of a pair of lowercase letters
      ' Put it at the position of the previous lowercase letter
      ' and put that letter at this letter's position
      MID$(text$, lowerIndex, 1) = char$
      MID$(text$, i, 1) = lowerLetter$
      lowerIndex = 0
    END IF
  END IF
NEXT i

PRINT text$
DLosc
quelle
2

C ++ 11 (GCC), 154 149 Bytes

#include<algorithm>
[](std::string s){int*p,u,l=u=-1;for(auto&c:s)(c|32)-97<26U?p=&(c&32?u:l),~*p?(std::swap(c,s[*p]),*p=-1):*p=&c-&s[0]:0;return s;}
Vaultah
quelle
1
Sie sollten entweder auch #include<string>oder zu C ++ 14 wechseln und ein generisches Lambda deklarieren [](auto s)und annehmen s, dass es von ist std::string. Das Deklarieren [](auto&s)erspart Ihnen außerdem die Rückgabe der Zeichenfolge als modifizierende Eingabeargumente, die als Ausgabe dienen sollen.
Karl Napf
2

Qbasic, 436 408 Bytes

LINE INPUT a$:b=len(a$):FOR a=1TO b:t$=MID$(a$,a,1)
IF"@"<t$AND"[">t$THEN
b$=b$+"U":u$=u$+t$
ELSEIF"`"<t$AND"{">t$THEN
b$=b$+"L":l$=l$+t$
ELSE b$=b$+t$
END IF:NEXT
FOR x=1TO b STEP 2:g$=g$+MID$(u$,x+1,1)+MID$(u$,x,1):h$=h$+MID$(l$,x+1,1)+MID$(l$,x,1):NEXT
FOR x=1TO b:t$=MID$(b$,x,1)
IF"U"=t$THEN
u=u+1:z$=z$+MID$(g$,u,1)
ELSEIF"L"=t$THEN l=l+1:z$=z$+MID$(h$,l,1)
ELSE z$=z$+t$
END IF:NEXT:?z$

Dank DLosc ein Byte gespart. Weitere Einsparungen durch Änderung der Behandlung von Nicht-Buchstaben-Zeichen.

Dies besteht im Wesentlichen aus drei Teilen:

  • Aufteilen der Eingabe in 3 Zeichenfolgen (Großbuchstaben, Kleinbuchstaben und eine Karte (die auch die anderen Zeichen enthält))
  • Spiegeln der Groß- und Kleinbuchstaben
  • Verwenden Sie die Karte, um die Ausgabe (neu) zu konstruieren.

Eine ausführlichere Erklärung (beachten Sie, dass dies eine frühere Version des Codes ist, das Prinzip jedoch weiterhin gilt):

' --- Part I: Reading the input
LINE INPUT a$
'This FOR loop takes one character at a time
b=len(a$):FOR a=1TO b
' And checks in what category the character belongs
t$=MID$(a$,a,1):SELECT CASE t$
' For each group, char t$ is added to that group (u$ for uppercase, 
' l$ for lowercase. The map in b$ is updated with a U or L on this index,
' or with the non-letter char t$.
CASE"A"TO"Z":b$=b$+"U":u$=u$+t$
CASE"a"TO"z":b$=b$+"L":l$=l$+t$
CASE ELSE:b$=b$+t$
END SELECT:NEXT

' --- Part II: Swapping within case-groups
' Loop through u$ and l$ twp chars at a time, and add those chunks in reverse order
' to g$ and h$. Because mid$ doesn't fail past the end of a string (but returns ""), 
' this automatically compensates for odd-length groups.
FOR x=1TO b STEP 2:g$=g$+MID$(u$,x+1,1)+MID$(u$,x,1):h$=h$+MID$(l$,x+1,1)+MID$(l$,x,1):NEXT

' --- Part III: Read the map to put it all back together
FOR x=1TO b:t$=MID$(b$,x,1)
' See what group was in this spot, then read the next char from the flipped string.
' This keeps an index on those strings for the next lookup.
IF t$="U"THEN
u=u+1:z$=z$+MID$(g$,u,1)
ELSEIF t$="L"THEN l=l+1:z$=z$+MID$(h$,l,1)
' The map contains a non-letter char, just drop that in
ELSE z$=z$+t$
' And finally,display the end result.
END IF:NEXT:?z$
steenbergh
quelle
2

PHP, 108 93 83 Bytes

<?=preg_replace([$a="/([a-z])([^a-z]*)([a-z])/",strtoupper($a)],"$3$2$1",$argv[1]);

Vorherige Version (93 Bytes)

<?=preg_replace(["/([a-z])([^a-z]*)([a-z])/","/([A-Z])([^A-Z]*)([A-Z])/"],"$3$2$1",$argv[1]);

Vielen Dank an @ user59178, der mich daran erinnert hat, dass preg_replace()Arrays von Strings als Argumente verwendet werden können.


Die ursprüngliche Antwort (108 Bytes)

$f=preg_replace;echo$f("/([a-z])([^a-z]*)([a-z])/",$r="$3$2$1",
$f("/([A-Z])([^A-Z]*)([A-Z])/",$r,$argv[1]));

Der Code wird hier eingepasst, um dem verfügbaren Platz zu entsprechen.
Es kann von der Kommandozeile ausgeführt werden:

$ php -d error_reporting=0 -r '$f=preg_replace;echo$f("/([a-z])([^a-z]*)([a-z])/",$r="$3$2$1",$f("/([A-Z])([^A-Z]*)([A-Z])/",$r,$argv[1]));' 'lLEhW OroLd!'

Eine um 1 Byte kürzere Version ist unter PHP 7 möglich, indem die Zuweisung $finnerhalb des ersten Aufrufs unterdrückt wird:

echo($f=preg_replace)("/([a-z])([^a-z]*)([a-z])/",$r="$3$2$1",
$f("/([A-Z])([^A-Z]*)([A-Z])/",$r,$argv[1]));

Beide Lösungen, mit Testfällen und ungolfed Versionen, sind auf Github zu finden .

Axiac
quelle
1
preg_replaceSie können eine Reihe von Ersetzungen vornehmen, damit Sie nur einen Anruf benötigen. Außerdem ist es kürzer zu bedienen <?=als echo. Mit diesen ist es einfach, Ihre Antwort auf 93 Bytes zu reduzieren.
user59178
Da hast du recht preg_replace(). Ich habe es vergessen. Ich mag es nicht <?=(meiner Meinung nach <?ist es nicht Teil der Sprache, es ist nur ein Marker) und ich schreibe gerne kurze einzeilige Programme, die über die Befehlszeile ausgeführt werden können php -r. Aber für den Code Golf sind Sie wieder richtig. Ich kann mit 1 Byte sparen <?=.
Axiac
1

Mathematica, 96 Bytes

s[#,r="([a-z])(.*?)([a-z])"]~(s=StringReplace[#,RegularExpression@#2->"$3$2$1"]&)~ToUpperCase@r&

Ein Port von Leos Retina-Antwort , der reguläre Ausdrücke verwendet.

Greg Martin
quelle
Ich bin ehrlich überrascht, dass Mathematica keine eingebauten Funktionen dafür hat. Ich meine, wenn "Wann ist Ostersonntag", "Wann ist der Sonnenuntergang" und "Was ist die Form von Frankreich" eingebaute Funktionen haben, sollte dies auch der Fall sein!
sagiksp
1

Bohne , 83 Bytes

Hexdump:

00000000 26 53 d0 80 d3 d0 80 a0 5d 20 80 0a a1 81 81 00  &SÐ.ÓÐ. ] ..¡...
00000010 23 81 01 20 80 0a a1 81 81 02 23 81 01 a8 db c1  #.. ..¡...#..¨ÛÁ
00000020 ad da dd a9 a8 db de c1 ad da dd aa bf a9 a8 db  .ÚÝ©¨ÛÞÁ.Úݪ¿©¨Û
00000030 c1 ad da dd 29 a4 b3 a4 b2 a4 31 a8 db e1 ad fa  Á.ÚÝ)¤³¤²¤1¨Ûá.ú
00000040 dd a9 a8 db de e1 ad fa dd aa bf a9 a8 db e1 ad  Ý©¨ÛÞá.úݪ¿©¨Ûá.
00000050 fa dd 29                                         úÝ)
00000053

Entsprechendes JavaScript:

a.replace(/([A-Z])([^A-Z]*?)([A-Z])/g,'$3$2$1').replace(/([a-z])([^a-z]*?)([a-z])/g,'$3$2$1')

Erläuterung:

Implizit die erste Eingabezeile als unformatiert aannehmen (da Zeilenumbrüche nicht Teil einer verschlüsselten Zeichenfolge sein können) und implizit die unverschlüsselte Zeichenfolge durch sequentielles Ersetzen von Paaren aus Großbuchstaben und Kleinbuchstaben ausgeben.

Probieren Sie die Demo hier aus.

Probieren Sie hier die Testsuite aus.

Patrick Roberts
quelle
1

Ruby, 81 Bytes

puts f=->(i,s){i.gsub /([#{s})([^#{s}*)([#{s})/,'\3\2\1'}[f[$*[0],'a-z]'],'A-Z]']
Axiac
quelle
1

JavaScript (ES6), 80 Byte

Basierend auf der Antwort von Leo auf Retina .

s=>eval("s"+(r=".replace(/([A-Z])([^A-Z]*)([A-Z])/g,'$3$2$1')")+r.toLowerCase())

Das funktioniert , weil das nur Großbuchstaben in dem Code .replace(/([A-Z])([^A-Z]*)([A-Z])/g,'$3$2$1')sind Aund Z, die verwendet werden , um die Zeichenbereiche zu beschreiben. Genau das müssen wir in Kleinbuchstaben umwandeln, um den zweiten Durchgang zu verarbeiten.

Testfälle

Arnauld
quelle
Es stellt sich heraus, dass es dieser Python-Antwort von Dennis sehr ähnlich ist .
Arnauld
1

ES6 155 - 195 Bytes

Ich weiß, dass es bereits eine bessere Antwort gibt, aber ich wollte es ohne Regex versuchen. Dieser arbeitet auch an Interpunktion, aber das scheint den (^_^)Test zu verletzen . In diesem Fall habe ich eine andere c()Funktion, die unten angegeben ist.

f=(s)=>{d={};s=[...s];for(i in s){b=s[i];for(j in s)if(i<j&!d[i]&c(s[j])==c(b)){d[j]=1;s[i]=s[j];s[j]=b;break}}return s.join('')}
c=c=>~(c.charCodeAt()/32)

f("M I'o DaG") //> I'M a GoD
f("(^_^)")     //> )_^^(

c=c=>((c!=c.toUpperCase())<<1|c!=c.toLowerCase())||c.charCodeAt()

f("M I'o DaG") //> I'M a GoD
f("(^_^)")     //> (^_^)

Erläuterung

f=(s)=>{
    d={};        //list of indexes already swapped
    s=[...s];        //string to array, stolen from above ES6 answer
    for(i in s){
        b=s[i];        //keep a note of what we are swapping
        for(j in s)        //iterate over the array again
            if( i<j & !d[i] & c(s[j])==c(b) ){
                        //only pay attention after we pass i'th
                        //only swap if this char hasn't been swapped
                        //only swap if both chars in same 'category'
                d[j]=1;        //note that the latter char has been swapped
                s[i]=s[j];
                s[j]=b;
                break        //avoid swapping on the same 'i' twice
            }
    }
    return s.join('')        //return as string
}
M3D
quelle
1

Perl 6 , 56 Bytes

{for "A".."Z","a".."z" ->@c {s:g/(@c)(.*?)(@c)/$2$1$0/}}

Nimmt eine Zeichenfolgenvariable als Argument und ändert sie direkt, sodass die Variable nach dem Aufrufen des Lambda das Ergebnis enthält.

Länger als in Perl, weil:

  • Die neue regex Syntax ist ausführlicher, zum Beispiel die Zeichenklassen auszuschreiben aussehen würde , <[A..Z]>statt [A-Z].
  • Regexe sind erstklassiger Quellcode, der zur Kompilierungszeit analysiert wird, und eine Zeichenfolge kann zur Laufzeit nur dann in sie interpoliert werden, wenn sie aus einem in sich geschlossenen Subregex besteht (dh Sie können eine Zeichenfolge nicht in eine Zeichenklasse interpolieren).
  • Explict EVAL, das mehr Flexibilität ermöglichen würde, erfordert das golfunfreundliche use MONKEY-SEE-NO-EVAL;Pragma.

Ein Array in einer @Variablen kann direkt in einem regulären Ausdruck referenziert werden und wird als Alternative behandelt.


Perl 6 , 65 Bytes

{reduce ->$_,@c {S:g/(@c)(.*?)(@c)/$2$1$0/},$_,"A".."Z","a".."z"}

Funktionsversion (gibt das Ergebnis als Rückgabewert des Lambda aus).

smls
quelle
1

R, 343 Bytes

Schrecklich ungeschickte R-Lösung:

f <- function(x) {
        y=unlist(strsplit(x,""))
        z=data.frame(l=ifelse(y %in% letters,0,ifelse(y %in% LETTERS,1,2)),s=y)
        l <- list(which(z$l==0),which(z$l==1))
        v <- unlist(l)
        for(j in 1:2) for (i in seq(1,ifelse(length(l[[j]])%%2==1,length(l[[j]])-2,length(l[[j]])-1),2)) l[[j]][i:(i+1)] <- rev(l[[j]][i:(i+1)])
        z[v,] <- z[unlist(l),]
        return(z$s)
    }

f("D's mroyr, Ivam. I'e faardi I act'n od htta.")

# [1] I ' m   s o r r y ,   D a v e .   I ' m   a f r a i d   I   c a n ' t   d o   t h a t .
Anzahl
quelle
1

Python 2, 181 Bytes

Viel länger als es sein sollte aber trotzdem:

def F(s):
 for l in[i for i,c in enumerate(s)if c.isupper()],[i for i,c in enumerate(s)if c.islower()]:
  for a,b in zip(l[0::2],l[1::2]):s=s[:a]+s[b]+s[a+1:b]+s[a]+s[b+1:]
 print s

Dadurch werden zunächst zwei Listen erstellt: eine der Indizes für die Großbuchstaben und eine für die Kleinbuchstaben. Jede dieser Listen wird in Indexpaaren durchlaufen, und die Zeichen an diesen Indizes werden umgeschaltet.

Ich werde morgen Golf spielen , aber jetzt ist es Zeit zu schlafen .

Daniel
quelle
1

Pip , 28 Bytes

Y[XLXU]aRy.`.*?`.y{Sa@0a@va}

Übernimmt die Eingabe als Befehlszeilenargument. Probieren Sie es online!

Erläuterung

Dies ist eine Regex-Lösung, die die integrierten Regex-Variablen XL(Kleinbuchstaben `[a-z]`) und XU(Großbuchstaben `[A-Z]`) verwendet.

                              a is 1st cmdline arg; v is -1 (implicit)
Y[XLXU]                       Yank a list containing XL and XU into y
         y.`.*?`.y            Concatenate y, `.*?`, and y itemwise, giving this list:
                              [`[a-z].*?[a-z]`; `[A-Z].*?[A-Z]`]
       aR                     In a, replace matches of each regex in that list...
                  {        }  ... using this callback function:
                   Sa@0a@v     Swap the 0th and -1st characters of the match
                          a    and return the resulting string
                              Print (implicit)

Wenn das zweite Argument Reine Liste ist, werden die Ersetzungen in Reihe durchgeführt. Daher stören sich die Ersetzung von Kleinbuchstaben und die Ersetzung von Großbuchstaben nicht gegenseitig.

DLosc
quelle
1

AWK , 121 129 Bytes

BEGIN{FS=OFS=""}{for(a=1;a<=NF;a++){if($a~/[A-Z]/?U>0?p=U+(U=0):0*(U=a):$a~/[a-z]/?L>0?p=L+(L=0):0*(L=a):0>0){t=$a;$a=$p;$p=t}}}1

Probieren Sie es online! Hinweis: Link verfügt über 8 zusätzliche Bytes, um eine mehrzeilige Eingabe zu ermöglichen

Die Verwendung ist recht typisch, erfordert jedoch eine Version AWK, die eine leere Zeichenfolge als Feldtrennzeichen akzeptiert (die meisten Versionen von, gawkaber ich bin mir ziemlich sicher, dass das Original AWKfehlschlagen würde :()

Es ist sehr einfach, da es einfach jedes Zeichen durchläuft und prüft, ob es zuvor einen dieser Fälle gefunden hat. In diesem Fall werden die Zeichen ausgetauscht und der aktivierte Index zurückgesetzt. Auf der Lernseite habe ich in nie eine Zuweisungsanweisung innerhalb einer Zuweisungsanweisung verwendetAWK . Aus irgendeinem Grund war es nie aufgetaucht. :)

Möglicherweise kann ich ein paar Bytes rasieren, indem ich OFS und FS außerhalb eines BEGINBlocks über eine Befehlszeilenzuweisung oder Ähnliches zuordnete, aber auf diese Weise ist es "sauberer".

Das Hinzufügen des TIO-Links zeigte mir, dass ich einen Transkriptionsfehler hatte, für dessen Behebung 8 Bytes erforderlich waren :( (habe ich ausgelassen 0*(U=a):)

Robert Benson
quelle
1

C (GCC) , 212 206 Bytes

  • Dank Ceilingcat für das Golfen von sechs Bytes.
#define I(a,b)if(S[j=i]>=a&S[i]<-~b){for(;S[++j]<a|S[j]>b;);j<l?s[i]=S[j],s[j]=S[i]:0;}
i,j,l;f(char*S){char*s=calloc(l=-~strlen(S),1);for(i=~0;++i<strlen(S);)if(!s[i]){s[i]=S[i];I(65,90)I(97,'z')}puts(s);}

Probieren Sie es online!

Jonathan Frech
quelle
@ceilingcat Vielen Dank.
Jonathan Frech
1

Stax , 18 Bytes

âß:}\]ó☺æ■jφ╛jz/Φi

Führen Sie es aus und debuggen Sie es

Der allgemeine Ansatz basiert auf Regex.

  • Zwei mal machen:
  • Alle Übereinstimmungen für finden [a-z].*?[a-z].
  • Tauschen Sie das erste und das letzte Zeichen in Übereinstimmungen aus.
  • Fall umkehren.
rekursiv
quelle
1

R , 223 163 Bytes 148 Bytes

EDIT: -60 Bytes durch Implementierung einer for-Schleife

EDIT: -15 Bytes von Giuseppe

u=utf8ToInt(scan(,''));for(i in c(65,97)){l=which(u%in%i:(i+25));x=sum(l|1)%/%2;u[l[1:(x*2)]]=u[c(matrix(l,2)[2:1,1:x])]};cat(intToUtf8(u,T),sep="")

Probieren Sie es online!

Testet, ob Zeichen in Klein- oder Großbuchstaben geschrieben sind, platziert sie in einer Matrix und invertiert die Matrix, um die Werte in einem vertauschten Format zu extrahieren. Dann mit ausgeben cat. Versuchen Sie es online mit Kämpfen, scan(,'')wenn der Code mehr als eine Zeile ist, daher die Semikolons in der einzelnen Codezeile.

Sumner18
quelle
Ich bekomme 168 auf Ihren Link, aber dieser Golf ist 163
Giuseppe
Und das bringt es auf 162.
Giuseppe
das funktioniert wahrscheinlich; Das xFummeln ist das Schlaue, aber es hat auch m=matrix4 Bytes gekostet.
Giuseppe
Was ist mit dem scan(,'')Problem? Und die Reduzierung der "LLEHW OROLD!" in tio zu scan(,'')oder auf andere weise eingabe bekommen?
Sumner,
0

Java 7, 117 Bytes

String c(String s){String x="([a-z])(.*?)([a-z])",y="$3$2$1";return s.replaceAll(x,y).replaceAll(x.toUpperCase(),y);}

EDIT: Ich habe gerade bemerkt, dass ich eine ähnliche Antwort wie @Leos Retina-Antwort habe , obwohl ich selbstständig darüber nachgedacht habe.

Ungolfed:

String c(final String s) {
  String x = "([a-z])(.*?)([a-z])",
         y = "$3$2$1";
  return s.replaceAll(x, y).replaceAll(x.toUpperCase(), y);
}

Testcode:

Probieren Sie es hier aus.

class M{
  static String c(String s){String x="([a-z])(.*?)([a-z])",y="$3$2$1";return s.replaceAll(x,y).replaceAll(x.toUpperCase(),y);}

  public static void main(String[] a){
    System.out.println(c("lLEhW OroLd!"));
    System.out.println(c("rpGOZmaimgn uplRzse naC DEoO LdGf"));
    System.out.println(c("eIt uqHKC RBWOO xNf ujPMO SzRE HTL EOvd yAg"));
    System.out.println(c("NraWgCi: Nsas-eNEiTIsev rNsiTG!!"));
    System.out.println(c("(^_^)"));
    System.out.println(c("AWCTY HUOS RETP"));
    System.out.println(c("hwn oeesd acsp nawyya"));
    System.out.println(c("SpMycaeIesKyBorekn"));
    System.out.println(c("D's mroyr, Ivam. I'e faardi I act'n od htta."));
  }
}

Ausgabe:

hELlO WorLd!
prOGRamming puzZles anD COdE GoLf
tHe quICK BROWN fOx juMPS OvER THE LAzy dOg
WarNiNg: Case-sENsITive sTriNG!!
(^_^)
WATCH YOUR STEP
who needs caps anyway
MySpaceKeyIsBroken
I'm sorry, Dave. I'm afraid I can't do that.
Kevin Cruijssen
quelle