60 lines
2.1 KiB
Cython
Executable File
60 lines
2.1 KiB
Cython
Executable File
#cython: language_level=3
|
|
|
|
cimport cython
|
|
from obitools3.dms.view.view cimport Line
|
|
from obitools3.utils cimport bytes2str_object, str2bytes, tobytes
|
|
from obitools3.dms.column.column cimport Column_line, Column_multi_elts
|
|
|
|
import sys
|
|
|
|
cdef class TabFormat:
|
|
|
|
def __init__(self, header=True, bytes NAString=b"NA", bytes sep=b"\t"):
|
|
self.header = header
|
|
self.first_line = True
|
|
self.NAString = NAString
|
|
self.sep = sep
|
|
|
|
@cython.boundscheck(False)
|
|
def __call__(self, object data):
|
|
|
|
line = []
|
|
|
|
if self.first_line:
|
|
self.tags = [k for k in data.keys()]
|
|
|
|
for k in self.tags:
|
|
|
|
if self.header and self.first_line:
|
|
if isinstance(data.view[k], Column_multi_elts):
|
|
keys = data.view[k].keys()
|
|
keys.sort()
|
|
for k2 in keys:
|
|
line.append(tobytes(k)+b':'+tobytes(k2))
|
|
else:
|
|
line.append(tobytes(k))
|
|
else:
|
|
value = data[k]
|
|
if isinstance(data.view[k], Column_multi_elts):
|
|
keys = data.view[k].keys()
|
|
keys.sort()
|
|
if value is None: # all keys at None
|
|
for k2 in keys: # TODO could be much more efficient
|
|
line.append(self.NAString)
|
|
else:
|
|
for k2 in keys: # TODO could be much more efficient
|
|
if value[k2] is not None:
|
|
line.append(str2bytes(str(bytes2str_object(value[k2])))) # genius programming
|
|
else:
|
|
line.append(self.NAString)
|
|
else:
|
|
if value is not None:
|
|
line.append(str2bytes(str(bytes2str_object(value))))
|
|
else:
|
|
line.append(self.NAString)
|
|
|
|
if self.first_line:
|
|
self.first_line = False
|
|
|
|
return self.sep.join(value for value in line)
|