Jak mówi Ignacio, tak, ale nie trywialnie za jednym zamachem. Problem polega na tym, że potrzebujesz wznowienia, aby określić, czy jesteś na ograniczniku z odgraniczeniem, czy nie, a podstawowy string.split
nie zapewnia tej funkcji.
Jeśli nie jest to wewnątrz ciasnej pętli, więc wydajność nie jest istotnym problemem, możesz to zrobić najpierw dzieląc ograniczniki, a następnie wykonując podział, a następnie łącząc. Brzydki kod demo:
# Bear in mind this is not rigorously tested!
def escaped_split(s, delim):
# split by escaped, then by not-escaped
escaped_delim = '\\'+delim
sections = [p.split(delim) for p in s.split(escaped_delim)]
ret = []
prev = None
for parts in sections: # for each list of "real" splits
if prev is None:
if len(parts) > 1:
# Add first item, unless it's also the last in its section
ret.append(parts[0])
else:
# Add the previous last item joined to the first item
ret.append(escaped_delim.join([prev, parts[0]]))
for part in parts[1:-1]:
# Add all the items in the middle
ret.append(part)
prev = parts[-1]
return ret
s = r'http\://www.example.url:ftp\://www.example.url'
print (escaped_split(s, ':'))
# >>> ['http\\://www.example.url', 'ftp\\://www.example.url']
Alternatywnie, łatwiej byłoby podążać za logiką, jeśli po prostu podzielisz strunę ręcznie.
def escaped_split(s, delim):
ret = []
current = []
itr = iter(s)
for ch in itr:
if ch == '\\':
try:
# skip the next character; it has been escaped!
current.append('\\')
current.append(next(itr))
except StopIteration:
pass
elif ch == delim:
# split! (add current to the list and reset it)
ret.append(''.join(current))
current = []
else:
current.append(ch)
ret.append(''.join(current))
return ret
Zauważ, że ta druga wersja zachowuje się nieco inaczej, gdy napotka podwójnych ucieczek następnie separatora: Funkcja ta pozwala uciec znaków ewakuacyjnych, tak że escaped_split(r'a\\:b', ':')
powraca ['a\\\\', 'b']
, ponieważ pierwszy \
ucieka drugi, pozostawiając :
należy interpretować jako prawdziwy ogranicznik. To jest coś, na co trzeba uważać.
Tak, ale nie trywialnie bez dalszego ograniczenia kryteria. –
@ Ignacio Vaazquez-Abrams jakie ograniczenia należy zastosować, aby było łatwiej? –
Myślę, że podział regex może obsłużyć to nie ma problemu? http://docs.python.org/2/library/re.html –