【问题标题】:How to decode a numpy array of encoded literals/strings in Python3? AttributeError: 'numpy.ndarray' object has no attribute 'decode'如何在 Python3 中解码编码文字/字符串的 numpy 数组? AttributeError:“numpy.ndarray”对象没有属性“解码”
【发布时间】:2017-03-16 06:54:07
【问题描述】:

在 Python 3 中,我有以下 NumPy 数组 strings

NumPy 数组中的每个string 都采用b'MD18EE 的形式,而不是MD18EE

例如:

import numpy as np
print(array1)
(b'first_element', b'element',...)

通常,人们会使用.decode('UTF-8') 来解码这些元素。

但是,如果我尝试:

array1 = array1.decode('UTF-8')

我收到以下错误:

AttributeError: 'numpy.ndarray' object has no attribute 'decode'

如何从NumPy 数组中解码这些元素? (也就是我不要b''

编辑:

假设我正在处理PandasDataFrame,其中只有某些以这种方式编码的列。例如:

import pandas as pd
df = pd.DataFrame(...)

df
        COL1          ....
0   b'entry1'         ...
1   b'entry2'
2   b'entry3'
3   b'entry4'
4   b'entry5'
5   b'entry6'

【问题讨论】:

    标签: arrays python-3.x pandas numpy unicode


    【解决方案1】:

    你有一个字节串数组; dtype 是S:

    In [338]: arr=np.array((b'first_element', b'element'))
    In [339]: arr
    Out[339]: 
    array([b'first_element', b'element'], 
          dtype='|S13')
    

    astype 可以轻松地将它们转换为 unicode,这是 Py3 的默认字符串类型。

    In [340]: arr.astype('U13')
    Out[340]: 
    array(['first_element', 'element'], 
          dtype='<U13')
    

    还有一个字符串函数库——将对应的str方法应用于字符串数组的元素

    In [341]: np.char.decode(arr)
    Out[341]: 
    array(['first_element', 'element'], 
          dtype='<U13')
    

    astype 更快,但decode 允许您指定编码。

    另见How to decode a numpy array of dtype=numpy.string_?

    【讨论】:

    • astype 方法似乎对字节长度信息过于具体。例如,如果我的输入 dtype 是 '|S1' 而不是 '|S13' 怎么办?
    • @John,看起来我们不必指定长度:np.array('one', 'S7').astype('U')
    • 我在某个字节数组上尝试了 astype('U') 并得到 UnicodeDecodeError: 'ascii' codec can't decode byte 0xe9 in position 0: ordinal not in range(128)。但是 np.char.decode(arr) 工作正常。
    【解决方案2】:

    如果您希望结果是 (Python) 字符串列表,您可以使用列表推导:

    >>> l = [el.decode('UTF-8') for el in array1]
    >>> print(l)
    ['element', 'element 2']
    >>> print(type(l))
    <class 'list'>
    

    或者,如果您想将其保留为 Numpy 数组,您可以使用np.vectorize 制作矢量化解码器函数:

    >>> decoder = np.vectorize(lambda x: x.decode('UTF-8'))
    >>> array2 = decoder(array1)
    >>> print(array2)
    ['element' 'element 2']
    >>> print(type(array2))
    <class 'numpy.ndarray'>
    

    【讨论】:

    • 谢谢!我正在使用 numpy 数组并将其放入 pandas 数据框中。也许有更快的捷径?按列转换?
    • 您的意思是“运行得更快”中的更快还是“更少的代码”中的更快?因为这两种方法都是单行的,所以打印语句只是为了表明它们有效:)
    • :) 我在想跑得更快。但是,我认为这种方法效果很好——这似乎是 Python2/Python3 的副作用,所以我怀疑其他人也遇到了这个问题。
    • 无论如何,使用decoder 会给我这个错误:AttributeError: 'numpy.void' object has no attribute 'decode'
    • 嗯,在这种情况下,看起来您的数组根本不是字符串数组,而是字符串数组和voids - 但我相信您能够修改解码器以处理这些。无论如何,我认为解决此问题的最佳(可能也是最快)方法是确保您在任何地方都使用字符串,而不是字节。你将如何做到这一点取决于你的数据来自哪里以及你如何阅读它。
    猜你喜欢
    • 2019-02-02
    • 1970-01-01
    • 1970-01-01
    • 2020-09-21
    • 2021-11-30
    • 1970-01-01
    • 2023-03-16
    • 1970-01-01
    • 2014-12-31
    相关资源
    最近更新 更多