#下载包
pip freeze > requestments.txt # 编辑此文件对需要的包进行删减
pip download -r requirements.txt -d /tmp/paks/ #下载requirements.txt中包至 /tmp/paks/下
# 导入新环境
pip install --no-index --find-links=/packs/ pandas 或
pip install --no-index --find-links=/packs/ -r requirements.txt (也可能是 --find-link)
# 在线安装
pip install -r requirements.txt
pip install pythonModuleName (==version) -i https://mirrors.aliyun.com/pypi/simple
---------------
或将下面代码放入:C:\Users\Administrator\AppData\Local\pip, 新建文件pip.ini中。
[global]
timeout = 6000
index-url = https://pypi.tuna.tsinghua.edu.cn/simple
trusted-host = pypi.tuna.tsinghua.edu.cn
Linux and Unix
~/.cache/pip
OS X
~/Library/Caches/pip
Windows
%LocalAppData%\pip\Cache
先从git 官网下载git.exe, 并安装,后配置环境变量如下:
;C:\Program Files\Git\bin\git.exe;C:\Program Files\Git\cmd
重启cmd。
进入pytorch的官网,选择要安装的版本并匹配好。
根据CUDA的版本选择cudnn,
windows:
torch.from_numpy()
arry. numpy()
import numpy as np
import torch
np_arr = np.array([1,2,3,4])
tor_arr=torch.from_numpy(np_arr)
tor2numpy=tor_arr.numpy()
print('\nnumpy\n',np_arr,'\ntorch\n',tor_arr,'\nnumpy\n',tor2numpy)
CUDA: 进入cuda_toolkit官网,找到你要下载的cuda.
collate_fn:如何取样本的,我们可以定义自己的函数来准确地实现想要的功能。default_collate会将labels分割合并转换成tensor。因此,如果是ndarray会将batchsize 内的array cat到一起。如果是list,会分割,可能不会得到想要的矩阵。因此,如果labels的shape固定,可以在此之前做成array的形式,不会导致错误。
from torch.utils.data import DataLoader
import numpy as np
import os
import torch
import cv2
from glob import glob
class MyDataset(DataLoader):
"""
"""
def __init__(self, img_folder, lab_folder, transform=None):
self.transform = transform
ll = glob(img_folder)
# read labels first, if there is no labels.
lab_names = os.listdir(lab_folder)
self.imgs = []
for id, lab_name in enumerate(lab_names):
file_first_name = str(lab_name).split('.')[0]
lab_abspath= os.path.join(lab_folder, lab_name)
bbs = self._read_line(lab_abspath)
if bbs is []:
continue
img_abspath = os.path.join(img_folder, file_first_name+'.png')
self.imgs.append((img_abspath, bbs))
def __getitem__(self, index):
fn, label = self.imgs[index]
img = cv2.imread(fn)
img = cv2.resize(img,(400, 400))
if self.transform is not None:
img = self.transform(img)
return img, label
def __len__(self):
return len(self.imgs)
def _read_line(self, path, pass_obj=['Others', ]):
"""
Parse the labels from file.
:param pass_obj: pass the labels in the list.
e.g. pass_obj=['Others','Pedestrian']
:param path: the path of file that need to parse.
:return:lists of the classes and the key points.
"""
file_open = open(path, 'r')
bbs = []
for line in file_open.readlines():
tmps = line.strip().split(' ')
if tmps[0] in pass_obj:
continue
box_x1 = float(tmps[4])
box_y1 = float(tmps[5])
box_x2 = float(tmps[6])
box_y2 = float(tmps[7])
bbs.append([tmps[0], box_x1, box_y1, box_x2, box_y2])
return bbs
def collect_fn(batches):
imgs = []
labs = []
for i, batch in enumerate(batches):
m = batch[0]
imgs.append(m)
labs.append(batch[1])
images = torch.from_numpy(np.asarray(imgs))
return images, labs
# 使用zip的技巧使代码简单。
def collate_fn_2(batch):
imgs, labels = zip(*batch)
return torch.from_numpy(np.asarray(imgs)), list(labels)
mydata=MyDataset('../../datasets/kitti/training/image_2/',
'../../datasets/kitti/training/label_2/')
traindata = DataLoader(dataset=mydata, batch_size=10,collate_fn=collect_fn, shuffle=False)
data = iter(traindata)
i, l = next(data) # 其中default_collate会将labels分割合并转换成tensor。collate_fn:如何取样本的,我们可以定义自己的函数来准确地实现想要的功能
# or use the next code.
# for i, data in enumerate(traindata):
# print(data[0].size, data[1].shape)
上面代码就不会导致labels做成tensor时失败。
zip() 函数用于将可迭代的对象作为参数,将对象中对应的元素打包成一个个元组,然后返回由这些元组组成的列表。
如果各个迭代器的元素个数不一致,则返回列表长度与最短的对象相同,利用 * 号操作符,可以将元组解压为列表。
a = [1,2,3]
b = [4,5,6]
c = [4,5,6,7,8]
zip(a,b) # 打包为元组的列表
#[(1, 4), (2, 5), (3, 6)]
zip(a,c) # 元素个数与最短的列表一致
#[(1, 4), (2, 5), (3, 6)]
zip(*zipped) # 与 zip 相反,*zipped 可理解为解压,返回二维矩阵式
#[(1, 2, 3), (4, 5, 6)]
l = ['a', 'b', 'c', 'd', 'e','f']
print l
#打印列表
print zip(l[:-1],l[1:])
输出结果:
['a', 'b', 'c', 'd', 'e', 'f']
[('a', 'b'), ('b', 'c'), ('c', 'd'), ('d', 'e'), ('e', 'f')]
nums = ['flower','flow','flight']
for i in zip(*nums):
print(i)
输出结果:
('f', 'f', 'f')
('l', 'l', 'l')
('o', 'o', 'i')
('w', 'w', 'g')
使用zip的技巧使代码简单,如上上个代码。
关于Python 的知识可参考:W3C school
a = [1, 2, 3]
a is a list
list->ndarray
b=np.asarray(a)
zip = (1, 2, 3)
c = list(zip)
tuple也是一个class,是不可变的list类型,不可以增删改。
创建:
tup1 = (‘physics’, ‘chemistry’, 1997, 2000);
tup2 = (1, 2, 3, 4, 5 );
tup3 = “a”, “b”, “c”, “d”;
访问:(与list一样)tup1[1:5];
修改:不可以修改,只能增加新的部分;
tup3 = tup1 + tup2;
print tup3;
easydict的作用:可以使得以属性的方式去访问字典的值!
>>> from easydict import EasyDict as edict
>>> d = edict({'foo':3, 'bar':{'x':1, 'y':2}})
>>> d.foo
3
>>> d.bar.x
1
>>> d = edict(foo=3)
>>> d.foo
3
解析json目录时很有用
>>> from easydict import EasyDict as edict
>>> from simplejson import loads
>>> j = """{
"Buffer": 12,
"List1": [
{"type" : "point", "coordinates" : [100.1,54.9] },
{"type" : "point", "coordinates" : [109.4,65.1] },
{"type" : "point", "coordinates" : [115.2,80.2] },
{"type" : "point", "coordinates" : [150.9,97.8] }
]
}"""
>>> d = edict(loads(j))
>>> d.Buffer
12
>>> d.List1[0].coordinates[1]
54.9
也可以这样用
>>> d = EasyDict()
>>> d.foo = 3
>>> d.foo
3
>>> d = EasyDict(log=False)
>>> d.debug = True
>>> d.items()
[('debug', True), ('log', False)]
>>> class Flower(EasyDict):
... power = 1
...
>>> f = Flower({'height': 12})
>>> f.power
1
>>> f['power']
1
参考:https://pypi.org/project/easydict/1.2/
Tqdm 是 Python 进度条库,可以在 Python 长循环中添加一个进度提示信息用法:tqdm(iterator)
# 方法1:
import time
from tqdm import tqdm
for i in tqdm(range(100)):
time.sleep(0.01)
方法2:
import time
from tqdm import trange
for i in trange(100):
time.sleep(0.01)
结果:
0%| | 0/100 [00:00, ?it/s]
11%|█ | 11/100 [00:00<00:00, 100.00it/s]
22%|██▏ | 22/100 [00:00<00:00, 100.00it/s]
32%|███▏ | 32/100 [00:00<00:00, 100.00it/s]
43%|████▎ | 43/100 [00:00<00:00, 100.00it/s]
54%|█████▍ | 54/100 [00:00<00:00, 100.00it/s]
64%|██████▍ | 64/100 [00:00<00:00, 99.11it/s]
74%|███████▍ | 74/100 [00:00<00:00, 99.37it/s]
85%|████████▌ | 85/100 [00:00<00:00, 99.56it/s]
95%|█████████▌| 95/100 [00:00<00:00, 99.69it/s]
100%|██████████| 100/100 [00:01<00:00, 99.70it/s]
可以为进度条设置描述:
import time
from tqdm import tqdm
pbar = tqdm(["a", "b", "c", "d"])
for char in pbar:
# 设置描述
pbar.set_description("Processing %s" % char)
time.sleep(1)
结果:
0%| | 0/4 [00:00, ?it/s]
Processing a: 25%|██▌ | 1/4 [00:01<00:03, 1.00it/s]
Processing b: 50%|█████ | 2/4 [00:02<00:02, 1.00it/s]
Processing c: 75%|███████▌ | 3/4 [00:03<00:01, 1.00it/s]
Processing d: 100%|██████████| 4/4 [00:04<00:00, 1.00it/s]
手动控制进度:
import time
from tqdm import tqdm
# 一共200个,每次更新10,一共更新20次
with tqdm(total=200) as pbar:
for i in range(20):
pbar.update(10)
time.sleep(0.1)
#方法2:
pbar = tqdm(total=200)
for i in range(20):
pbar.update(10)
time.sleep(0.1)
close() 不要也没出问题?
pbar.close()
结果:
0%| | 0/200 [00:00, ?it/s]
15%|█▌ | 30/200 [00:00<00:01, 150.00it/s]
25%|██▌ | 50/200 [00:00<00:01, 130.43it/s]
30%|███ | 60/200 [00:00<00:01, 119.52it/s]
40%|████ | 80/200 [00:00<00:01, 112.91it/s]
50%|█████ | 100/200 [00:00<00:00, 108.70it/s]
55%|█████▌ | 110/200 [00:01<00:00, 105.93it/s]
65%|██████▌ | 130/200 [00:01<00:00, 104.08it/s]
75%|███████▌ | 150/200 [00:01<00:00, 102.82it/s]
80%|████████ | 160/200 [00:01<00:00, 101.96it/s]
85%|████████▌ | 170/200 [00:01<00:00, 96.38it/s]
90%|█████████ | 180/200 [00:01<00:00, 97.44it/s]
100%|██████████| 200/200 [00:01<00:00, 98.19it/s]
扩展阅读:https://blog.csdn.net/langb2014/article/details/54798823?locationnum=8&fps=1
OS.path的应用
os.path.abspath(path) 返回绝对路径
os.path.basename(path) 返回path最后的文件名
os.path.commonprefix(list) 返回list(多个路径)中,所有path共有的最长的路径
os.path.dirname(path) 返回文件路径
os.path.exists(path) 如果路径 path 存在,返回 True;如果路径 path 不存在,返回 False。
os.path.lexists 路径存在则返回True,路径损坏也返回True
os.path.expanduser(path) 把path中包含的"~"和"~user"转换成用户目录
os.path.expandvars(path) 根据环境变量的值替换path中包含的"$name"和"${name}"
os.path.getatime(path) 返回最近访问时间(浮点型秒数)
os.path.getmtime(path) 返回最近文件修改时间
os.path.getctime(path) 返回文件 path 创建时间
os.path.getsize(path) 返回文件大小,如果文件不存在就返回错误
os.path.isabs(path) 判断是否为绝对路径
os.path.isfile(path) 判断路径是否为文件
os.path.isdir(path) 判断路径是否为目录
os.path.islink(path) 判断路径是否为链接
os.path.ismount(path) 判断路径是否为挂载点
os.path.join(path1[, path2[, ...]]) 把目录和文件名合成一个路径
os.path.normcase(path) 转换path的大小写和斜杠
os.path.normpath(path) 规范path字符串形式
os.path.realpath(path) 返回path的真实路径
os.path.relpath(path[, start]) 从start开始计算相对路径
os.path.samefile(path1, path2) 判断目录或文件是否相同
os.path.sameopenfile(fp1, fp2) 判断fp1和fp2是否指向同一文件
os.path.samestat(stat1, stat2) 判断stat tuple stat1和stat2是否指向同一个文件
os.path.split(path) 把路径分割成 dirname 和 basename,返回一个元组
os.path.splitdrive(path) 一般用在 windows 下,返回驱动器名和路径组成的元组
os.path.splitext(path) 分割路径,返回路径名和文件扩展名的元组
os.path.splitunc(path) 把路径分割为加载点与文件
os.path.walk(path, visit, arg) 遍历path,进入每个目录都调用visit函数,visit函数必须有3个参数(arg, dirname, names),dirname表示当前目录的目录名,names代表当前目录下的所有文件名,args则为walk的第三个参数
os.path.supports_unicode_filenames 设置是否支持unicode路径名
类似tensorflow指定GPU的方式,使用CUDA_VISIBLE_DEVICES。
1、直接终端中设定:
CUDA_VISIBLE_DEVICES=1 python main.py
2、python代码中设定:
import os
os.environ["CUDA_VISIBLE_DEVICES"] = "2"
3、使用函数 set_device
import torch
torch.cuda.set_device(id)
参考:http://www.cnblogs.com/darkknightzh/p/6591923.html
方法一:round()函数
以下展示了使用 round() 方法的实例:
#!/usr/bin/python
print "round(80.23456, 2) : ", round(80.23456, 2)
print "round(100.000056, 3) : ", round(100.000056, 3)
print "round(-100.000056, 3) : ", round(-100.000056, 3)
以上实例运行后输出结果为:
round(80.23456, 2) : 80.23
round(100.000056, 3) : 100.0
round(-100.000056, 3) : -100.0
方法二:’%.2f’ %f 方法
f = 1.23456
print('%.4f' % f)
print('%.3f' % f)
print('%.2f' % f)
a = torch.Tensor([1,2,3,4,5,6,7,7,8])
b = torch.Tensor([1,2])
c = [a, b]
out = torch.cat(c,dim=0)
结果:
out:torch.Tensor([1,2,3,4,5,6,7,7,8, 1, 2 ])
Python中numpy数组的合并有很多方法,如
np.append()
np.concatenate((a,b),axis=1)
np.stack()
np.hstack((a,b))
np.vstack((a,b))
np.dstack()
time.strftime('%Y_%m_%d_%r',time.localtime(time.time()))
%y 两位数的年份表示(00-99)
%Y 四位数的年份表示(000-9999)
%m 月份(01-12)
%d 月内中的一天(0-31)
%H 24小时制小时数(0-23)
%I 12小时制小时数(01-12)
%M 分钟数(00=59)
%S 秒(00-59)
from torchsummary import summary
summary(model, input_size=(3,224,224), batch_size=-1, device='cuda')
简单地讲,yield 的作用就是把一个函数变成一个 generator,带有 yield 的函数不再是一个普通函数,Python 解释器会将其视为一个 generator,调用 fab(5) 不会执行 fab 函数,而是返回一个 iterable 对象!在 for 循环执行时,每次循环都会执行 fab 函数内部的代码,执行到 yield b 时,fab 函数就返回一个迭代值,下次迭代时,代码从 yield b 的下一条语句继续执行,而函数的本地变量看起来和上次中断执行前是完全一样的,于是函数继续执行,直到再次遇到 yield。
def batch_iter(x, y, batch_size=64):
"""生成批次数据"""
data_len = len(x)
num_batch = int((data_len - 1) / batch_size) + 1
indices = np.random.permutation(np.arange(data_len))
x_shuffle = x[indices]
y_shuffle = y[indices]
for i in range(num_batch):
start_id = i * batch_size
end_id = min((i + 1) * batch_size, data_len)
yield x_shuffle[start_id:end_id], y_shuffle[start_id:end_id]
Method1: use scatter_ function
labels = [0, 1, 4, 7, 3, 2]
one_hot = torch.zeros(6, 8).scatter_(dim = 1, index = labels, value = 1)
Method2: use index_select() funtion
labels = [0, 1, 4, 7, 3, 2]
index = torch.eye(8)
one_hot = torch.index_select(index, dim = 0, index = labels)
Method3: use Embedding module
emb = nn.Embedding(8, 8)
emb.weight.data = torch.eye(8)
then we can get
emb(Variable(torch.LongTensor([1, 2], [3, 4])))
Variable containing:
(0,.,.) =
0 1 0 0 0 0 0 0
0 0 1 0 0 0 0 0
(1 ,.,.) =
0 0 0 1 0 0 0 0
0 0 0 0 1 0 0 0
Method4: create a module
class One_Hot(nn.Module):
def __init__(self, depth):
super(One_Hot,self).__init__()
self.depth = depth
self.ones = torch.sparse.torch.eye(depth)
def forward(self, X_in):
X_in = X_in.long()
return Variable(self.ones.index_select(0,X_in.data))
def __repr__(self):
return self.__class__.__name__ + "({})".format(self.depth)
获取Github相关网站的ip
访问https://www.ipaddress.com,拉下来,找到页面中下方的“IP Address Tools – Quick Links”
分别输入github.global.ssl.fastly.net和github.com& codeload.github.com,查询ip地址
修改本地hosts文件C:\Windows\System32\drivers\etc
参考如下,增加github.global.ssl.fastly.net和github.com的映射。
# Github
199.232.5.194 github.global.ssl.fastly.net
192.30.253.112 github.com
140.82.114.10 codeload.github.com
更新DNS缓存(貌似不更新也可以,会自动更新)
命令行输入:ipconfig /flushdns
如题 : getattr(self,‘layer’+str(l))
torch.mul(a, b)是矩阵a和b对应位相乘,a和b的维度必须相等,比如a的维度是(1, 2),b的维度是(1, 2),返回的仍是(1, 2)的矩阵,
torch.mm(a, b)是矩阵a和b矩阵相乘,比如a的维度是(1, 2),b的维度是(2, 3),返回的就是(1, 3)的矩阵
torchvision.utils.make_grid(tensor, nrow=8, padding=2, normalize=False, range=None, scale_each=False, pad_value=0)
制作图像网格。
参数说明:
tensor (Tensor or list) – 4D小批量形状Tensor张量(B x C x H x W)或所有大小相同的图像列表。
nrows (int, optional) – 网格中的行数。最终的网格大小(B / nrow,nrow)。默认值是8。
normalize (bool, optional) – 如果TRUE,将图像移到范围(0, 1)中,减去最小值并除以最大像素值。
range (tuple, optional) – 元组(min,max),其中min和max是数字,然后使用这些数字对图像进行标准化。默认情况下,min和max是从张量计算的。
scale_each (bool, optional) – 如果TRUE,则在批处理图像中分别缩放每个图像,而不是在所有图像上(最小、最大)缩放图像。
pad_value (float, optional) – 填充像素的值。
查看下面的例子:
torchvision.utils.save_image(tensor, filename, nrow=8, padding=2, normalize=False, range=None, scale_each=False, pad_value=0)
将给定的Tensor张量保存到图像文件中。 参数说明:
Tensor (张量或者列表) – 要保存的图像。如果小批量的Tensor张量,调用make_grid把Tensor张量存储为网格图像。