Pergunta

Eu preciso ser capaz de tomar uma string como:

'''foo, bar, "one, two", three four'''

em:

['foo', 'bar', 'one, two', 'three four']

Eu tenho um sentimento (com dicas de #python) que a solução vai envolver o módulo shlex.

Foi útil?

Solução

A solução módulo shlex permite aspas escapou, uma citação escapar outra, e todos os suportes do escudo fantasia coisas.

>>> import shlex
>>> my_splitter = shlex.shlex('''foo, bar, "one, two", three four''', posix=True)
>>> my_splitter.whitespace += ','
>>> my_splitter.whitespace_split = True
>>> print list(my_splitter)
['foo', 'bar', 'one, two', 'three', 'four']

escapou citações exemplo:

>>> my_splitter = shlex.shlex('''"test, a",'foo,bar",baz',bar \xc3\xa4 baz''',
                              posix=True) 
>>> my_splitter.whitespace = ',' ; my_splitter.whitespace_split = True 
>>> print list(my_splitter)
['test, a', 'foo,bar",baz', 'bar \xc3\xa4 baz']

Outras dicas

Depende de como complicado você quer começar ... você quer para permitir que mais de um tipo de citar. Como cerca de citações escaparam?

sua sintaxe se parece muito com o formato de arquivo comum CSV, que é apoiado pela biblioteca padrão Python:

import csv
reader = csv.reader(['''foo, bar, "one, two", three four'''], skipinitialspace=True)
for r in reader:
  print r

Saídas:

['foo', 'bar', 'one, two', 'three four']

HTH!

Você também pode querer considerar a csv módulo. Eu não tentei, mas parece que os seus dados de entrada está mais perto de CSV do que a sintaxe shell (que é o que shlex parses).

Você poderia fazer algo parecido com isto:

>>> import re
>>> pattern = re.compile(r'\s*("[^"]*"|.*?)\s*,')
>>> def split(line):
...  return [x[1:-1] if x[:1] == x[-1:] == '"' else x
...          for x in pattern.findall(line.rstrip(',') + ',')]
... 
>>> split("foo, bar, baz")
['foo', 'bar', 'baz']
>>> split('foo, bar, baz, "blub blah"')
['foo', 'bar', 'baz', 'blub blah']

Eu diria que uma expressão regular seria o que você está procurando por aqui, embora eu não sou terrivelmente familiar com motor Regex do Python.

Assumindo que você use fósforos preguiçosos, você pode obter um conjunto de jogos em uma corda que você pode colocar em sua matriz.

Se ele não precisa ser bonito, isso pode levá-lo em seu caminho:

def f(s, splitifeven):
    if splitifeven & 1:
        return [s]
    return [x.strip() for x in s.split(",") if x.strip() != '']

ss = 'foo, bar, "one, two", three four'

print sum([f(s, sie) for sie, s in enumerate(ss.split('"'))], [])
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top