Tensorflow/Pytorch及python数据处理中问题及解决汇总(持续更新中)

博主在使用tensorflow进行深度学习编程的时候经常会遇到一些常见的问题,特此在这里将自己遇到的问题与解决方法进行汇总。

1、tensor张量维度扩展(试图把shape为[64,10]的张量扩展为[64,128,10]的张量)

n = tf.expand_dims(m,axis=1) #m为shape为[64,10]的tensor
#经过tf.expand_dims扩展后的shape为[64,1,10],axis控制增加哪一维度
mn = tf.tile(n,[1,128,1]) #128表示在第二维复制的次数,可以在不同的维度上根据自己的需要进行复制
#经过tf.tile扩展后的shape为[64,128,10]

2、使用梯度裁剪时,由于存在梯度不存在为None,如果使用tf.clip_by_value()时会出现错误:ValueError: None values not supported。

在这里的处理技巧是对梯度不存在为None时不做任何处理,即可避免这个问题。感谢https://stackoverrun.com/cn/q/10826383提供的解决方法,很受用。

opt_func = tf.train.AdamOptimizer(learning_rate=self.config.lr)
            gvs = opt_func.compute_gradients(self.loss)
            def ClipIfNotNone(grad):
                if grad is not None:
                    return tf.clip_by_value(grad, -10, 10)
            capped_gvs = [(ClipIfNotNone(grad), var) for grad, var in gvs]        
            self.optimizer = opt_func.apply_gradients(grads_and_vars=capped_gvs, global_step=self.global_step)

3、笔者在使用双向RNN中,出现这个错误。InvalidArgumentError: seq_lens() > input.dims()[[Node: hidden/bidirectional_rnn/bw/ReverseSequence。

是因为在对seq进行反转时,序列的长度要超过输入的长度。比如经过padding以后,输入的tensor为[64,100,300],然而你的未经padding的文本实际长度为120,这就导致在发展的时候出现此错误。我们可以考虑将tf.nn.bidirectional_dynamic_rnn()中的sequence_length中的最大值设置为100,就可以避免此问题。在这里特别感谢https://blog.csdn.net/weixin_40015791/article/details/88641806博文对我的帮助。

4、笔者最近在学习Pytorch时,遇到很多坑。比如报错之一的RuntimeError: Invalid device, must be cuda device,笔者在执行print(tensor1.cuda(tensor2.device))时报的错。

是因为在定义张量的时候,没有设置torch.Tensor分配到的设备的对象。解决方法如下:

import torch
device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")
#在定义tensor时候添加device值即可
attn=torch.tensor([[1.0,0.0,2.0,3.0],[3.0,3.0,3.0,3.0]],device = device)
a = torch.tensor([[[1],[2],[3],[4]],[[5],[6],[7],[8]]], device=device).float()
b = torch.tensor([[[1,2,3,4]],[[5,6,7,8]]], device=device).float()
c = torch.matmul(a,b)
c = c.eq(0)
print(c)
print(c.cuda(b.device))

5、笔者在Pycharm执行文件时可以执行,在cmd命令行执行时报错:ModuleNotFoundError: No module named 'xxx'。

原因是在命令行运行时,只是搜索当前路径,是找不到你需要导入的model的。解决方法就是在执行文件的开头添加如下代码

import sys
import os
curPath = os.path.abspath(os.path.dirname(__file__))
rootPath = os.path.split(curPath)[0]
sys.path.append(rootPath)

注意:根据自己文件目录格式上述代码可能有些不同。

6、如何将CSV文件与json格式文件,参考https://blog.csdn.net/huanbia/article/details/72674832

#group为读取的CSV文件后的数据,我们将其记为df,那么df.to_json(orient='records')后得到的是字符串
#格式如下'[{"columns1":"a","columns2":"b"},{"columns1":"c","columns2":"d"}...]'
string = group.to_json(orient='records')
#接着再使用json.loads将字符串转化为json格式,此时得到的是一个列表
string_list = json.loads(string)
得到的格式如下:[{"columns1":"a","columns2":"b"},{"columns1":"c","columns2":"d"}...]

7、在做NLP有关序列生成模型

笔者参考了seq2seq以及最近较为火爆的transformer模型,在encoder时一般会在setence的后端添加一个停止的符号一般有/等,不需要在文本开始的时候添加,在decoder时会添加一个开始的符号比如/等,而不需要在文本结尾的时候添加结束符号,后续在自己进行项目任务时需要注意这一点。

8.如何将列表(List)数据转化为数据框(Dataframe)格式?参考链接

第一种是将两个不同的列表转化为数据框

from pandas.core.frame import DataFrame
a=[1,2,3,4]#列表a
b=[5,6,7,8]#列表b
c={"a" : a,
   "b" : b}#将列表a,b转换成字典
data=DataFrame(c)#将字典转换成为数据框
print(data)

#结果
   a  b
0  1  5
1  2  6
2  3  7
3  4  8

第二种是将包含不同子列表的列表转换为数据框

from pandas.core.frame import DataFrame
a=[[1,2,3,4],[5,6,7,8]]#包含两个不同的子列表[1,2,3,4]和[5,6,7,8]
data=DataFrame(a)#这时候是以行为标准写入的
data=data.T#转置之后得到想要的结果
data.rename(columns={0:'a',1:'b'},inplace=True)#注意这里0和1都不是字符串
print(data)

#结果
a  b
0  1  5
1  2  6
2  3  7
3  4  8


9.json文件和字符串文件的相互转化,参考

"""json格式转为字符串"""
import json

data = [{
    'name' : 'ACME',
    'shares' : 100,
    'price' : 542.23
}]

json_str = json.dumps(data)
print(json_str)
# 输出
'[{"name": "ACME", "shares": 100, "price": 542.23}]'

"""字符串转化为json格式"""
ans = json.loads(json_str)
print(ans)
#输出

[{'name': 'ACME', 'price': 542.23, 'shares': 100}]

"""注意:读取json文件要用json.load()
   保存为json文件时要用json。dump() """




10.npy文件和npz文件保存

楼主在最近做项目时,保存npy和npz文件均正常,但是在load时,npy文件会报错:IndexError: only integers, slices (`:`), ellipsis (`...`), numpy.newaxis (`None`) and integer or boo......这是引文npy保存文件时数据类型不一致导致,我的解决方法是保存为npz文件,具体格式如下:

np.savez(save_path, arr_name1:np.array1,arr_name2:np.array2.......)

这样再load的时候就不会再报错

11、numpy求点乘距离时可以直接使用numpy中的乘法

常规做法:对于A矩阵,若求A矩阵与其他矩阵们的点乘时,需要A-B做点乘,A-C做点乘,A-D做点乘......

更新做法:对于A矩阵,先复制多份,new_A=[A for i in range(n)],再降B,C,D....汇聚成一起,n为B,C,D.......这些矩阵的数量,然后再直接点乘即可

 

你可能感兴趣的:(Tensorflow/Pytorch及python数据处理中问题及解决汇总(持续更新中))