Verketten von Zeichenfolgen mit dem Kontext

13

Zeichenfolgen mit Kontext

Für diese Herausforderung ist eine Zeichenfolge mit Kontext ein Tripel von Zeichenfolgen, die als linker Kontext , Datenteil und rechter Kontext bezeichnet werden . Es repräsentiert eine Teilzeichenfolge einer längeren Zeichenfolge. Wir verwenden die vertikale Pipe |als Trennzeichen. Ein Beispiel für eine Zeichenfolge mit Kontext ist also cod|e-go|lf, wo sich der linke Kontext cod, die Daten e-gound der rechte Kontext befinden lf. Dieses Beispiel repräsentiert die Teilzeichenfolge e-govon code-golf.

Um nun zwei Zeichenfolgen mit dem Kontext zu verknüpfen, gehen wir wie folgt vor, wobei wir aa|bcc|deeund cc|de|eeeals Beispiele verwenden. Wir richten die Zeichenfolgen wie im Diagramm aus

a a|b c c|d e e
      c c|d e|e e e

so dass ihre Datenteile benachbart sind. Der Datenteil der Verkettung ist in diesem Fall die Verkettung der Datenteile bccde. Der linke Kontext ist in diesem Fall der Teil, der sich weiter links vom ersten Datenteil erstreckt aa. Ebenso ist der richtige Kontext eee, also ist die Verkettung die Zeichenfolge mit dem Kontext aa|bccde|eee. Als zweites Beispiel betrachten Sie a|bb|cdund aabb|cd|, wobei das zweite Wort einen leeren rechten Kontext hat. Das Ausrichtungsdiagramm ist

  a|b b|c d
a a b b|c d|

wobei sich der linke Kontext des zweiten Wortes weiter erstreckt als der des ersten. Die Verkettung ist aa|bbcd|.

Aber warte, es gibt ein Problem: Wenn die Buchstaben des Ausrichtungsdiagramms nicht übereinstimmen, existiert die Verkettung nicht! Als ein Beispiel der Schaltbild aa|bb|ccund c|c|cIS

a a|b b|c c
      c|c|c

Wo die bund cin der vierten Spalte nicht übereinstimmen, können sie nicht verkettet werden.

Die Aufgabe

Ihre Aufgabe ist es, ein Programm zu schreiben, das zwei Zeichenfolgen mit Kontext enthält, deren Teile |wie oben voneinander getrennt sind , und deren Verkettung auszugeben, falls vorhanden, und etwas anderes, falls nicht. Das "etwas anderes" kann ein beliebiger Wert sein, einschließlich keiner Ausgabe, solange es sich nicht um eine gültige Zeichenfolge mit Kontext handelt und in allen Fällen dieselbe. Das Auslösen eines Fehlers ist jedoch nicht akzeptabel. Sie können entweder ein STDIN-zu-STDOUT-Programm oder eine Funktion angeben. Anonyme Funktionen werden ebenfalls akzeptiert. Die kleinste Byteanzahl gewinnt, und Standardlücken sind nicht zulässig.

Testfälle

aa|bcc|dee cc|de|eee -> aa|bccde|eee
a|bb|cd    aabb|cd|  -> aa|bbcd|
a|b|cccd   aab|cc|c  -> aa|bcc|cd
a|b|c      b||cd     -> a|b|cd
aa|bb|cc   c|c|c     -> None
aaa|b|c    abb|cd|d  -> None
|bb|cd     abb|c|ed  -> None
a|b|c      a||cd     -> None
Zgarb
quelle

Antworten:

4

Haskell, 184 182 201 199 155

s&t|(a,'|':b)<-f t,(x,'|':y)<-f$r s,x#b,a#y=r(y!r a)++b!r x|0<1=""
r=reverse
a!b=a++drop(length a-1)b
(#)a=and.zipWith(==)(r a).filter h
f=span h
h=(/='|')

Beispiellauf:

"|a|"&"|b|" -- returns "|ab|"
"|a|x"&"|b|" -- returns ""

Wenn es keine Übereinstimmung gibt, wird eine leere Zeichenfolge zurückgegeben. Andernfalls wird das Ergebnis zurückgegeben.

teilweise erklärung:

# ist eine Funktion, die zwei Zeichenfolgen erhält und zurückgibt, ob sie übereinstimmen oder nicht.

! Ruft zwei Zeichenfolgen ab und gibt die erste Zeichenfolge zurück, die mit einem zusätzlichen Zeichen aus der zweiten verknüpft ist (sofern vorhanden).

Die Hauptfunktion &Gebrauch span (/='|')die Eingänge in zwei Teile aufzuspalten, a|b|czu a, b|c, überprüft , ob die Kontexte entsprechen, und verwendet dann !zweimal um die Ausgabe zu montieren.

Edit: Magier-spätes Regolfing scheint ziemlich effektiv zu sein.

stolzer haskeller
quelle
Hmm, ich befürchte, dass das Auslösen eines Fehlers keine akzeptable Ausgabemethode ist, insbesondere für eine Funktion. Das Hinzufügen |1<2=""zur Definition von &sollte das lösen. Es tut mir leid, dass ich dies nicht expliziter in den Spezifikationen angegeben habe. Ich werde es in bearbeiten.
Zgarb
@ Zgarb Eigentlich würde dies nicht beheben. Wird eine Zeichenfolge mit zu vielen '|'Zeichen zurückgegeben, wenn die Zeichenfolgen nicht in Ordnung sind?
stolzer Haskeller
Sicher, solange es sich bei allen nicht übereinstimmenden Eingaben um dieselbe Zeichenfolge handelt.
Zgarb
3

Python (242 Bytes)

import itertools as i
s='|'
j=''.join
r=reversed
m=lambda a,b:j(j(*set(p+q))for p,q in i.izip_longest(a,b,fillvalue=''))
def c(A,B):
 u,v,w,x,y,z=(A+s+B).split(s)
 try:return j(r(m(r(u+v),r(x))))[:-len(v)]+s+v+y+s+m(w,y+z)[len(y):]
 except:0

Erläuterung

Die Lambda-Funktion mgibt die längere von zwei Zeichenfolgen zurück, solange sie ein gemeinsames Präfix haben. Es tut dies durch die leere Zeichenkette Verketten ''anstelle der fehlenden Werte, dann das Ergebnis drehen (die die Formen annehmen können aa, ab, a, oder bin Fällen der Übereinstimmung / Nichtübereinstimmung / ungleiche Länge) in einen Satz von eindeutigen Zeichen an jeder Position. joinErwartet ein einzelnes Argument. Wenn Sie also eine Menge mit mehr als einem Element entpacken, wird a ausgelöst TypeError.

Die Hauptfunktion dann

  • Anwendungen , mdie kombinieren linken Kontext und Datenteil das erste Wort , mit dem linken Kontext der zweiten (von rechts nach links über umgekehrt Strings)
  • verkettet Datenteile,
  • und wird erneut verwendet m, um den richtigen Kontext des ersten Wortes mit dem Datenteil und dem richtigen Kontext des zweiten Wortes zu kombinieren

Die Datenteile der beiden ursprünglichen Wörter werden von der rechten und linken Seite des neuen Kontexts abgeschnitten.

Da wir wissen, dass Fehlausrichtungen a auslösen m, TypeErrorfangen wir in diesen Fällen die Ausnahme ab und kehren implizit zurück None.

Testen

TESTCASES = [
    ('aa|bcc|dee', 'cc|de|eee', 'aa|bccde|eee'),
    ('a|bb|cd', 'aabb|cd|', 'aa|bbcd|'),
    ('a|b|cccd', 'aab|cc|c', 'aa|bcc|cd'),
    ('a|b|c', 'b||cd', 'a|b|cd'),
    ('aa|bb|cc', 'c|c|c', None),
    ('aaa|b|c', 'abb|cd|d', None),
    ('|bb|cd', 'abb|c|ed', None),
    ('a|b|c', 'a||cd', None),
]

for A, B, R in TESTCASES:
    print '{:<10} {:<9} -> {}'.format(A, B, c(A, B))

Ausgabe

aa|bcc|dee cc|de|eee -> aa|bccde|eee
a|bb|cd    aabb|cd|  -> aa|bbcd|  
a|b|cccd   aab|cc|c  -> aa|bcc|cd 
a|b|c      b||cd     -> a|b|cd    
aa|bb|cc   c|c|c     -> None      
aaa|b|c    abb|cd|d  -> None      
|bb|cd     abb|c|ed  -> None      
a|b|c      a||cd     -> None  
Greg
quelle