Вы могли бы, по крайней мере, частично обойти то, что делает модуль csv
, создав собственную версию одноэлементного None
-подобного класса/значения:
from __future__ import print_function
import csv
class NONE(object):
''' None-like class. '''
def __repr__(self): # Method csv.writer class uses to write values.
return 'NONE' # Unique string value to represent None.
def __len__(self): # Method called to determine length and truthiness.
return 0
NONE = NONE() # Singleton instance of the class.
if __name__ == '__main__':
try:
from cStringIO import StringIO # Python 2.
except ModuleNotFoundError:
from io import StringIO # Python 3.
data = [['None value', None], ['NONE value', NONE], ['empty string', '']]
f = StringIO()
csv.writer(f).writerows(data)
f = StringIO(f.getvalue())
print(" input:", data)
print("output:", [e for e in csv.reader(f)])
Полученные результаты:
input: [['None value', None], ['NONE value', NONE], ['empty string', '']]
output: [['None value', ''], ['NONE value', 'NONE'], ['empty string', '']]
Использование NONE
вместо None
позволит сохранить достаточно информации, чтобы вы могли отличить ее от любых фактических значений данных пустой строки.
Еще лучшая альтернатива…
Вы можете использовать тот же подход для реализации пары относительно легких «прокси»-классов csv.reader
и csv.writer
— необходимых, поскольку вы не можете создать подкласс встроенных классов csv
, написанных на C, — без больших накладных расходов (поскольку большая часть обработки по-прежнему будет выполняться нижележащими встроенными модулями). Это сделало бы то, что происходит, полностью прозрачным, поскольку все это инкапсулировано в прокси.
from __future__ import print_function
import csv
class csvProxyBase(object): _NONE = '<None>' # Unique value representing None.
class csvWriter(csvProxyBase):
def __init__(self, csvfile, *args, **kwrags):
self.writer = csv.writer(csvfile, *args, **kwrags)
def writerow(self, row):
self.writer.writerow([self._NONE if val is None else val for val in row])
def writerows(self, rows):
list(map(self.writerow, rows))
class csvReader(csvProxyBase):
def __init__(self, csvfile, *args, **kwrags):
self.reader = csv.reader(csvfile, *args, **kwrags)
def __iter__(self):
return self
def __next__(self):
return [None if val == self._NONE else val for val in next(self.reader)]
next = __next__ # Python2.x compatibility.
if __name__ == '__main__':
try:
from cStringIO import StringIO # Python 2.
except ModuleNotFoundError:
from io import StringIO # Python 3.
data = [['None value', None], ['empty string', '']]
f = StringIO()
csvWriter(f).writerows(data)
f = StringIO(f.getvalue())
print("input : ", data)
print("ouput : ", [e for e in csvReader(f)])
Полученные результаты:
input: [['None value', None], ['empty string', '']]
output: [['None value', None], ['empty string', '']]
person
martineau
schedule
08.07.2012