每当我读取包含一列字符串的 CSV 文件时,我发现默认情况下 pandas
会将其 dtype
指定为 object
。我尝试使用 mydf['mycol'].astype(str)
更改列 mycol
的 dtype
从 object
到 str
,但它不起作用 - 它没有给我一个错误,但同时,dtype
保持不变。
我读到 pandas
是在 numpy
之上构建的,并且 numpy
允许 str_
和unicode_
see here: numpy scalar types 。我不太熟悉 pandas 的内部工作原理,也不熟悉 numpy 一般来说。
- 使用
pandas.io.parsers.read_csv
时,我可以做些什么来确保 CSV 文件中的一列字符串被读取为dtype
str
而不是object
?
更具体地说,我需要使用哪些参数(来自下面给出的参数)来实现此目的?
pandas.io.parsers.read_csv(filepath_or_buffer, sep=', ', dialect=None,
compression=None, doublequote=True, escapechar=None, quotechar='"', quoting=0,
skipinitialspace=False, lineterminator=None, header='infer', index_col=None,
names=None, prefix=None, skiprows=None, skipfooter=None, skip_footer=0,
na_values=None, na_fvalues=None, true_values=None, false_values=None,
delimiter=None, converters=None, dtype=None, usecols=None, engine=None,
delim_whitespace=False, as_recarray=False, na_filter=True, compact_ints=False,
use_unsigned=False, low_memory=True, buffer_lines=None, warn_bad_lines=True,
error_bad_lines=True, keep_default_na=True, thousands=None, comment=None,
decimal='.', parse_dates=False, keep_date_col=False, dayfirst=False,
date_parser=None, memory_map=False, float_precision=None, nrows=None,
iterator=False, chunksize=None, verbose=False, encoding=None, squeeze=False,
mangle_dupe_cols=True, tupleize_cols=False, infer_datetime_format=False,
skip_blank_lines=True)
- 有些相关:
pandas.io.parsers.read_csv
的参数中是否有任何变量/标志可以自动从字符串列中读取丢失的字符串作为''
(空字符串)而不是将丢失的字符串读取为nan
?
此外,文档中未描述许多可以传递给 pandas.io.parsers.read_csv
的参数:pandas.io.parsers.read_csv.html例如na_fvalues
、use_unsigned
、compact_ints
等。除了阅读代码(有点长)之外,还有什么其他的吗?哪里有所有参数的更详细文档?
最佳答案
这是 Wes 做出的一项技术决定,不使用 numpy 的字符串数据类型:Numpy 将所有字符串分配为相同的大小。
在大多数现实世界的用例中,字符串的大小并不固定,而且通常有一些字符串非常长。分配一个非常大的连续内存块是浪费的(IIRC, 与直觉相反,可能会更慢!)将它们存储为固定大小:
In [11]: np.array(["ab", "a"]) # The 2 is the length
Out[11]:
array(['ab', 'a'],
dtype='|S2')
In [12]: np.array(['this is a very long string', 'a', 'b', 'c'])
Out[12]:
array(['this is a very long string', 'a', 'b', 'c'],
dtype='|S26')
举一个愚蠢的例子,我们可以看到一个对象数据类型占用更少内存的例子:
In [21]: a = np.array(['a'] * 99 + ['this is a very long string, really really really really really long, oh yes'])
In [22]: a.nbytes
Out[22]: 7500
In [23]: b = a.astype(object)
In [24]: b.nbytes + sum(sys.getsizeof(item) for item in b)
Out[24]: 4674
numpy 字符串还有一些“令人惊讶”的行为(也是由于它们的布局):
In [31]: a = np.array(['ab', 'c'])
In [32]: a[1] = 'def'
In [33]: a # what the f?
Out[33]:
array(['ab', 'de'],
dtype='|S2')
如果您想修复此行为 - 并保留 numpy 字符串 dtype - 您必须为每个作业创建一个副本。 (使用对象数组,您可以免费获得此功能:只需更改指针即可。)
因此,pandas 字符串是使用对象数据类型存储的。
注意:我认为文档中有一部分讨论了此决定,但我似乎找不到它......
关于python-3.x - 如何使 pandas read_csv 处理 numpy str(或 unicode)标量数据类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28614120/