首页 > 解决方案 > ValueError:从数据帧中提取 X 和 Y 时,代码需要是类似数组的整数

问题描述

我正在尝试通过使用可重现的数组示例来了解有关数据帧的更多信息。我正在做的是尝试从我的可重现示例中提取值 X 和 y 从我的数据框中枚举我的类,其中前 5 行是 A 类的特征,后 5 行是 B 类的特征。

我的实际数据框是这样的:

[[ 31,  25,  17,  62,  26,  23, 193, 143,  37,  29, 220, 216, 175, 195, 207, 198, 190, 222,
  178, 214]
 [ 31,  26,  19,  59,  25,  23, 193, 140,  37,  29, 220, 216, 174, 195, 207, 198, 190, 220,
  178, 214]
 [ 31,  23,  17,  67,  23,  22, 195, 147,  38,  31, 222, 215, 182, 195, 213, 198, 185, 221,
  178, 207]
 [ 31,  23,  19,  67,  23,  23, 194, 144,  37,  31, 222, 218, 179, 198, 216, 198, 186, 221,
  179, 207]
 [ 31,  28,  17,  65,  23,  22, 193, 142,  36,  31, 222, 217, 177, 195, 216, 196, 182, 220,
  174, 207]
 [ 16,  24,  33,  43,  43,  58, 163,  76,  57, 105, 205, 200, 193, 188, 186, 193, 182, 227,
  193, 227]
 [  9,  13,  22,  36,  13,  49, 163,  39,  33, 105, 204, 200, 193, 191, 188, 193, 183, 224,
  194, 227]
 [ 23,  17,  10,  28,  21,  40, 166,  46,  28, 102, 208, 206, 196, 198, 195, 202, 190, 225,
  196, 229]
 [ 25,  19,  11,  30,  23,  39, 166,  46,  26,  99, 208, 206, 199, 196, 198, 201, 189, 227,
  198, 231]
 [ 25,  20,  12,  31,  25,  40, 169,  48,  27, 101, 211, 206, 198, 198, 196, 202, 190, 226,
  198, 229]]

pd.DataFrame(my_array)

数据框图像

因此,我想做的是获取我自己的数据框,提取 X 和 y。我的特征是从 0 到 255 的像素强度,每列是从 1 到 20 的像素索引

我的问题是我无法理解如何相应地传递值。这就是我尝试的方式:

indices = ['class_A, class_B']
target_names = ['class_A, class_B']
pixel_index = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
X = pd.DataFrame(my_array, columns= pixel_index)
y = pd.Categorical.from_codes(indices,target_names)

索引应该是每个像素索引的类,我不确定它是否以正确的方式完成

给出的错误:

ValueError:代码需要是类似数组的整数

我想要实现的是,当我这样做时:

df = X.join(pd.Series(y, name='class'))

我得到了一个新的数据框,其中包含我以前的数据框的类。

当我将索引更改为整数并更正字符串参数时,我得到以下信息:

17   18   19   20    class  
0  190  222  178  214  class_A  
1  190  220  178  214  class_B  
2  185  221  178  207      NaN  
3  186  221  179  207      NaN  
4  182  220  174  207      NaN  
5  182  227  193  227      NaN  
6  183  224  194  227      NaN  
7  190  225  196  229      NaN  
8  189  227  198  231      NaN  
9  190  226  198  229      NaN 

但是,每 5 行由不同的类堆叠,例如前 5 行应为 A 类,后 5 行应为 B 类。

例如,当我执行 df.head 时,我想要实现的目标是:

   17   18   19   20    class  
    0  190  222  178  214  class_A  
    1  190  220  178  214  class_A  
    2  185  221  178  207  class_A   
    3  186  221  179  207  class_A   
    4  182  220  174  207  class_A   
    5  182  227  193  227  class_B 
    6  183  224  194  227  class_B  
    7  190  225  196  229  class_B  
    8  189  227  198  231  class_B  
    9  190  226  198  229  class_B 

标签: pythonpython-3.xpandasnumpydataframe

解决方案


原答案:

首先,您应该参考此文档

根据文档class_A可以调用0并且class_B可以调用1,因此indices = [0,1]这将解决Value Error

进一步的 target_names 没有正确定义,而不是

target_names = ['class_A, class_B'] 它应该是

target_names = ['class_A', 'class_B']

我相信你的问题的第二部分,你想将每一行加入一个类,长度indices应该等于观察的数量,即rows

例如 2 行的代码。

my_array = np.array([[ 31,  25,  17,  62,  26,  23, 193, 143,  37,  29, 220, 216, 175, 195, 207, 198, 190, 222,
                     178, 214], [ 31,  26,  19,  59,  25,  23, 193, 140,  37,  29, 220, 216, 174, 195, 207, 198, 190, 220,
                        178, 214]])

indices = [0,1]
target_names = ['class_A', 'class_B']
pixel_index = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
X = pd.DataFrame(my_array, columns= pixel_index)
y = pd.Categorical.from_codes(indices,target_names)

print(X.join(pd.Series(y,name='class')))

编辑:

正如所问的那样,数据集中有 10 行,前 5 行代表 class A,其余 5 行代表 class B

假设只有 10 行,您可以通过以下方式更改上面代码中的索引

indices = [0,0,0,0,0,1,1,1,1,1]

这将给出所讨论的预期结果。

假设行将更改 5 的倍数。例如,如果行从 10 增加到 15。那么您将需要索引和类动态更改。

我在下面创建了虚拟数据并添加了动态代码。

import string
import numpy as np
import pandas as pd                         

#random array generated with 15 rows (experiment by changing the rows)
my_array = np.random.rand(15,20)

#creating indices based on numbers of rows assuming the indice changes after every 5 rows
indices = sorted(list(range(0,int(my_array.shape[0]/5)))*5)

#creating a dict to assign each indice a class 
class_dict = dict(zip(range(0,int((my_array.shape[0]/5))), string.ascii_uppercase ))
target_names = ["Class_" + c for c in class_dict.values()]

pixel_index = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
X = pd.DataFrame(my_array, columns= pixel_index)
y = pd.Categorical.from_codes(indices,target_names)
print(X.join(pd.Series(y,name='class')))

推荐阅读