Как использовать Python CSV-модуль для разделения данных, разделенных двойной трубкой - PullRequest
7 голосов
/ 15 июня 2011

У меня есть данные, которые выглядят так:

"1234"||"abcd"||"a1s1"

Я пытаюсь читать и писать, используя программу чтения и записи CSV в Python. Поскольку ограничитель модуля csv ограничен одним символом, есть ли способ получить данные чисто? Я не могу позволить себе удалить пустые столбцы, так как это огромный массив данных, который должен обрабатываться с привязкой ко времени. Любые мысли будут полезны.

Ответы [ 4 ]

13 голосов
/ 15 июня 2011

Документы и эксперименты подтверждают, что разрешены только разделители с одним символом.

Поскольку cvs.reader принимает любой объект, поддерживающий протокол итератора, вы можете использовать синтаксис генератора для замены || -s с | -s, а затем передать этот генератор читателю:

def read_this_funky_csv(source):
  # be sure to pass a source object that supports
  # iteration (e.g. a file object, or a list of csv text lines)
  return csv.reader((line.replace('||', '|') for line in source), delimiter='|')

Этот код довольно эффективен, поскольку он работает на одной строке CSV за раз, при условии, что ваш источник CSV дает строкикоторые не превышают вашу доступную оперативную память:)

2 голосов
/ 15 июня 2011
>>> import csv
>>> reader = csv.reader(['"1234"||"abcd"||"a1s1"'], delimiter='|')
>>> for row in reader:
...     assert not ''.join(row[1::2])
...     row = row[0::2]
...     print row
...
['1234', 'abcd', 'a1s1']
>>>
1 голос
/ 01 июля 2012

Если ваши данные буквально выглядят как пример (поля никогда не содержат '||' и всегда заключаются в кавычки), и вы можете допустить кавычки или хотите вырезать их позже, просто используйте .split

>>> '"1234"||"abcd"||"a1s1"'.split('||')
['"1234"', '"abcd"', '"a1s1"']
>>> list(s[1:-1] for s in '"1234"||"abcd"||"a1s1"'.split('||'))
['1234', 'abcd', 'a1s1']

csv требуется только в том случае, если в полях найден разделитель или для удаления необязательных кавычек вокруг полей

1 голос
/ 15 июня 2011

К сожалению, разделитель представлен символом в C. Это означает, что невозможно иметь в нем что-либо, кроме одного символа в Python. Хорошей новостью является то, что можно игнорировать значения, которые являются нулевыми:

reader = csv.reader(['"1234"||"abcd"||"a1s1"'], delimiter='|')
#iterate through the reader.
for x in reader:
    #you have to use a numeric range here to ensure that you eliminate the 
    #right things.
    for i in range(len(x)):
        #Odd indexes will be discarded.
        if i%2 == 0: x[i] #x[i] where i%2 == 0 represents the values you want.

Есть и другие способы сделать это (например, можно написать функцию), но это дает вам необходимую логику.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...