python学习,日积月累

本文介绍Python中文件行数统计、CSV操作、日志记录、列表及排序处理等实用技巧,并深入讲解numpy数组特性、PIL图像处理、pandas数据帧操作。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

python 统计文件夹指定类型的文件总的行数

import os

number = 0 
types = ['py','yml','html','css']
def counts(path):
	# 获取当前目录所有子文件或文件夹名字
	files = os.listdir(path)
	# 遍历所有子文件名或文件夹名
	for name in files:
		cur_path = path + "/" + name
		# 判断是否是文件
		if os.path.isfile(cur_path):
			# 判断是否是python 文件
			end = cur_path.split(".")[-1]
			if end in types:
				# 	pass 
				# 现在统一计算,包括.py,.html,.yml,.css
				print(cur_path)
				# lines = getcount(cur_path)
				lines = len(open(cur_path,'rb').readlines())
				global number
				number += lines 

		elif os.path.isdir(cur_path):
			counts(cur_path)


# path = "../myReID/HAReID/" # 9349
path = "../myReID/backend/" # 2321 
counts(path)
print("total line number of {} is {}".format(path,number))
# total: 11670 

python 读写csv文件

在这里插入图片描述
1.读取表头的2中方式

#方式一
import csv
with open("test.csv") as f:
    reader = csv.reader(f)
    rows=[row for row in  reader]
    print(rows[0])


----------
#方式二
import csv
with open("test.csv") as f:
    #1.创建阅读器对象
    reader = csv.reader(f)
    #2.读取文件第一行数据
    head_row=next(reader)
    print(head_row)

2、读取某一列

#1.获取文件某一列数据
import csv
with open("test.csv") as f:
    reader = csv.reader(f)
    column=[row[0] for row in  reader]
    print(column)

3、写数据

#1.向csv文件中写入数据
import csv
with open("test.csv",'a') as f:
     row=['1','23','18','no','hhh',3,0,'Tops']
     write=csv.writer(f)
     write.writerow(row)
     print("写入完毕!")

imp.load_source()的使用

动态导入某个模块,通过绝对路径指定文件

m = imp.load_source('lib4',"D:/project/segmentation/code/Elib/lib4.py")
#通过绝对路径指令文件的位置
#返回的m是该模块的表示,lib4表示转化的的模块的名称,可以通过import导入
m.show()
import lib4 
lib4.show()
#上面的两种调用都是等效的

sys.path.append(insert)的使用

临时添加搜索路径,方便更简洁的import其他包和模块。这种方法导入的路径会在python程序退出后失效。

import sys
sys.path.append('..') #表示导入当前文件的上层目录到搜索路径中
sys.path.append('/home/model') # 绝对路径
sys.path.append(os.getcwd()) # 加入当前路径
sys.path.insert(1, "./model") # 前面的序号,表示优先级,0最高级

tf.app.flags 的使用

这个主要是调用tf定义的一个定义和解析参数的文件,可以快速定义参数和解析参数

#调用文件flags.py,可以快速定义参数类型,(参数名,默认值,tips)
	flags = tf.app.flags
	flags.DEFINE_string('data_dir', '/tmp/mnist', 'Directory with the MNIST data.')
	flags.DEFINE_integer('batch_size', 5, 'Batch size.')
	flags.DEFINE_integer('num_evals', 1000, 'Number of batches to evaluate.')
	#定义解析参数的实例
	FLAGS = flags.FLAGS

	print(FLAGS.data_dir, FLAGS.batch_size, FLAGS.num_evals)

/tmp/mnist 5 1000

if __name__ == '__main__':
    tf.app.run()

如果当前是从其它模块调用的该模块程序,则不会运行main函数!而如果就是直接运行的该模块程序,则会运行main函数.

tf.app.run() 其实执行程序中main函数,并解析命令行参数

logging 的使用

通过指定特定的格式,写到日志,方便debug

logging.basicConfig函数各参数:
filename: 指定日志文件名
filemode: 和file函数意义相同,指定日志文件的打开模式,‘w’或’a’
datefmt: 指定时间格式,同time.strftime()
level: 设置日志级别,默认为logging.WARNING
stream: 指定将日志的输出流,可以指定输出到sys.stderr,sys.stdout或者文件,默认输出到sys.stderr,当stream和filename同时指定时,stream被忽略
format: 指定输出的格式和内容,format可以输出很多有用信息,如上例所示:
%(levelno)s: 打印日志级别的数值
%(levelname)s: 打印日志级别名称
%(pathname)s: 打印当前执行程序的路径,其实就是sys.argv[0]
%(filename)s: 打印当前执行程序名
%(funcName)s: 打印日志的当前函数
%(lineno)d: 打印日志的当前行号
%(asctime)s: 打印日志的时间
%(thread)d: 打印线程ID
%(threadName)s: 打印线程名称
%(process)d: 打印进程ID
%(message)s: 打印日志信息

import logging
 
logging.basicConfig(level=logging.DEBUG,
                format='%(asctime)s %(filename)s[line:%(lineno)d] %(levelname)s %(message)s',
                datefmt='%a, %d %b %Y %H:%M:%S',
                filename='mycode.log',
                filemode='w')
    
logging.debug('This is debug message')
logging.info('This is info message')
logging.warning('This is warning message')

Mon, 21 Oct 2019 22:16:50 mycode.py[line:15] DEBUG This is debug message
Mon, 21 Oct 2019 22:16:50 mycode.py[line:16] INFO This is info message
Mon, 21 Oct 2019 22:16:50 mycode.py[line:17] WARNING This is warning message

列表问题

  1. list.extend(temp) 与 list.append(temp) 的区别
    对于extend ,参数是列表或者元组或集合,返回的结果是把列表或者元组里面的元素依次添加进列表里面。
    而append()的参数,将作为一个元素添加到列表末尾
    list1 = ["lhj","scc"]
    list2 = ["yq"]
    tuple1 = (1,3)
    set1 = {123,1234}
    list1.extend(list2)
    list1.extend(tuple1)
    list1.extend(set1)
    
    print("after merge:",list1)
    ------------------
    after merge: ['lhj', 'scc', 'yq', 1, 3, 1234, 123]
    
  2. 对列表排序
    如果列表的元素是一些可以比较大小的字母或者数字,可以直接调用sort,但是如果是一个多元组,如下:那么我们就要选定key来作为比较大小
    list1 = [('a',1),('c',5),('b',-1)]
    sort_list1 = sorted(list1,key=lambda item:item[0])
    sort_list2 = sorted(list1,key=lambda item:item[1],reverse=True)  # 反转
    print(sort_list1)    
    print(sort_list2)                             
    
    lambda是一个隐函数,是固定写法,不要写成别的单词;其后面的名字可以随便起,表示list的其中一个变量,然后通过:分隔,指定采用元素中的哪个值作为key,最后一个选择是否反转。默认是从小到大的排序。
    3. 学习ndarry
    这个博客写得好
    https://www.cnblogs.com/jcchoiling/p/5928452.html
    ndarry 与python 的列表最大的不同是列表可以是不同类型的元素
    ndarry 必须是相同的元素,他可以自动识别,把类行统一
    int -》float -》字符串
    arr1 = np.array([0,1,2])
    arr2 = np.array([0,1.5,2])
    arr3 = np.array([0,1.5,'2.8'])
    print(arr1)
    print(arr2)
    print(arr3)
    result:
    [0 1 2]
    [0.  1.5 2. ]
    ['0' '1.5' '2.8']
    
    当然我们可以手动改变类型 用astype()
    浮点到整型
    arr4 = np.array([1.1,2.3,3.4])
    arr5 = arr4.astype(np.int)
    #字符串到浮点型 # 注意字符串要么全部是整数要么全部是浮点数
    arr6 = np.array(['1.1','2.2','3.3'])
    arr7 = arr4.astype(np.float)
    print(arr7)
    # astype是复制了一个副本,在副本进行操作的
    
    # 元素访问跟list 一样,支持索引和切片
    print(arr7[2])
    # [n:m] [n,m)
    print(arr7[:2])
    
    array 和 asarray 的区别
    他们都是将结构数据转化为ndarray
    主要区别是当数据源是ndarray的时候,array仍然会复制出一个副本,占用新的内存
    但是asarry 不会,但是如果改变了数据类型,asarray也会复制副本
    但如果源不是ndarray 那么都会复制一个副本
      data = [1,2,3]
      d1 = np.array(data)
      d2 = np.asarray(data)
      data[1] = 0
      print(data,d1,d2)
      reuslt:
      [1.1 2.3]
      [1, 0, 3] [1 2 3] [1 2 3]
      
      arr1 = np.ones((2,2),np.int32)
      arr2 = np.array(arr1)
      arr3 = np.asarray(arr1)
      arr4 = np.asarray(arr1,np.float)
      arr1[1] = 2
      print(arr1)
      print(arr2)
      print(arr3)
      print(arr4)
      result:
      [[1 1]
       [2 2]]
      [[1 1]
       [1 1]]
      [[1 1]
       [2 2]]
      [[1. 1.]
       [1. 1.]]
    

PIL 的 Image 基本使用

from PIL import Image
import param

def  readimg():
	filepath = param.local_img + "confu.jpg"
	img = Image.open(filepath)

	# img.show()

	# 查看图片的属性
	'''
	format: 以 string 返回图片档案的格式(JPG, PNG, BMP, None, etc.);如果不是从打开文件得到的实例,则返回 None。
	mode: 以 string 返回图片的模式(RGB, CMYK, etc.);完整的列表参见 官方说明·图片模式列表
	size: 以二元 tuple 返回图片档案的尺寸 (width, height)
	palette: 仅当 mode 为 P 时有效,返回 ImagePalette 示例
	info: 以字典形式返回示例的信息
	'''
	# 一般有,format,mode ,size,palette,info 等属性
	print(img.format,img.mode,img.size,img.palette,img.info)

	# 保存图片
	# 如下就改变了图片的格式,是图片实例本身才有的save方法
	# 通过使用thumbnail 函数接收一个二元组把图片缩小为特定大小的图片
	w,h = img.size
	img.thumbnail((w//2,h//2))
	img.save(param.local_img+"confu.png")
	print(img.size)

	# 裁剪图片函数,crop
	#(xmin,ymin,xmax,ymax) x-width
	cropimg = img.crop((0,0,50,100))
	cropimg.save(param.local_img+"cropimg.jpg")

def transpose():
	img = Image.open(param.local_img+"confu.jpg")
	w,h = img.size
	mid = w // 2
	leftbox = (0,0,mid,h)
	rightbox = (mid,0,w,h)
	newleft = (0,0,w-mid,h)# 存在不整除的情况
	newright = (w-mid,0,w,h)
	# 裁剪左边图片,左右翻转,然后旋转180度
	partleft = img.crop(leftbox).transpose(Image.FLIP_LEFT_RIGHT).transpose(Image.ROTATE_180)
	# 裁剪右边图片
	partright = img.crop(rightbox)

	# 贴图
	img.paste(partleft,newright)
	img.paste(partright,newleft)

	img.show()

# readimg()
transpose()

#http://effbot.org/imagingbook/image.htm  模块说明文档

os.walk()

os.walk(top[, topdown=True[, onerror=None[, followlinks=False]]])

用于通过在目录树中游走输出在目录中的文件名,向上或者向下。

  • top – 是你所要遍历的目录的地址, 返回的是一个三元组(root,dirs,files)。

    • root 所指的是当前正在遍历的这个文件夹的本身的地址
    • dirs 是一个 list ,内容是该文件夹中所有的目录的名字(不包括子目录)
    • files 同样是 list , 内容是该文件夹中所有的文件(不包括子目录)
  • topdown --可选,为 True,则优先遍历 top 目录,否则优先遍历 top 的子目录(默认为开启)。如果 topdown 参数为 True,walk 会遍历top文件夹,与top 文件夹中每一个子目录。

  • onerror – 可选,需要一个 callable 对象,当 walk 需要异常时,会调用。

  • followlinks – 可选,如果为 True,则会遍历目录下的快捷方式(linux 下是软连接 symbolic link )实际所指的目录(默认关闭),如果为 False,则优先遍历 top 的子目录。
    在这里插入图片描述

for root,dirs,files in os.walk(".\img"):
		for name in files:
			print(os.path.join(root,name))
output:
.\img\confu.jpg
.\img\1\confu.png
.\img\2\cropimg.jpg			

pandas的数据结构DataFrame详解


import pandas as pd
def dataframe():

	# 1、DataFrame的创建方式
	# 1.1 通过二维数组创建
	print("1、DataFrame的创建方式")
	arr = [['张伊曼', 100], ['张诗诗', 90], ['张巧玲', 80]]
	df0 = pd.DataFrame(arr)
	print("df0===========================")
	print(df0)
	# 1.2 通过字典创建
	dict0 = {
    'android': [90, 80, 60],
    'java': [99, 78, 89],
    'python': [98, 82, 85],
    'c': 80
	}
	df0 = pd.DataFrame(dict0)
	print("df0===========================")
	print(df0)
    '''
    1、DataFrame的创建方式
	df0===========================
	     0    1
	0  张伊曼  100
	1  张诗诗   90
	2  张巧玲   80
	df0===========================
	   android  java  python   c
	0       90    99      98  80
	1       80    78      82  80
	2       60    89      85  80
    '''  
	# 2、基本属性
	print("2、基本属性")
	arr = [['张伊曼', 100], ['张诗诗', 90], ['张巧玲', 80]]
	df0 = pd.DataFrame(arr)
	print("df0===========================")
	print(df0)

	print("df0.index===========================")  #如果不指定index的值,就会从默认0开始
	print(df0.index)

	print("df0.columns===========================")  #如果不指定columns的值,就会从默认0开始
	print(df0.columns)

	print("df0.dtypes===========================")   #以列为单位算起,数据类型
	print(df0.dtypes)

	print("df0.values===========================")
	print(df0.values)

	print("更换index、columns的值===========================")
	df0 = pd.DataFrame(arr,index=['第一行','第二行','第三行'],columns=['name','分散'])
	#df0.index = ['第一行', '第二行', '第三行']  #等同于以这种方式更改index的值
	print(df0)
	'''
	2、基本属性
	df0===========================
	     0    1
	0  张伊曼  100
	1  张诗诗   90
	2  张巧玲   80
	df0.index===========================
	RangeIndex(start=0, stop=3, step=1)
	df0.columns===========================
	RangeIndex(start=0, stop=2, step=1)
	df0.dtypes===========================
	0    object
	1     int64
	dtype: object
	df0.values===========================
	[['张伊曼' 100]
	 ['张诗诗' 90]
	 ['张巧玲' 80]]
	更换index、columns的值===========================
	    name   分散
	第一行  张伊曼  100
	第二行  张诗诗   90
	第三行  张巧玲   80
	'''
	# 3、DataFrame的值的获取
	print("3、DataFrame的值的获取")
	dict0 = {
	    'android': [90, 80, 60],
	    'java': [99, 78, 89],
	    'python': [98, 82, 85],
	    'c': 80
	}
	df0 = pd.DataFrame(dict0)
	df0.index = ['张伊曼', '张诗诗', '张巧玲']
	print("df0===========================")
	print(df0)

	# print(df0['张伊曼']['android'])  #注意:先行后列获取会报错

	print("单个的值的获取===========================")
	print(df0['android']['张伊曼'])    #通过这种方式获取单个的值

	print("一行值的获取===========================")
	print(df0.ix[0])

	print("多行值的获取===========================")
	print(df0.ix[:2])

	print("任意多行值的获取===========================")
	print(df0.ix[:2, :2])

	print("一列值的获取===========================")
	print(df0['android'])
	print("修改单个值===========================")
	'''
	3、DataFrame的值的获取
	df0===========================
	     android  java  python   c
	张伊曼       90    99      98  80
	张诗诗       80    78      82  80
	张巧玲       60    89      85  80
	单个的值的获取===========================
	90
	一行值的获取===========================
	android    90
	java       99
	python     98
	c          80
	Name: 张伊曼, dtype: int64
	多行值的获取===========================
	     android  java  python   c
	张伊曼       90    99      98  80
	张诗诗       80    78      82  80
	任意多行值的获取===========================
	     android  java
	张伊曼       90    99
	张诗诗       80    78
	一列值的获取===========================
	张伊曼    90
	张诗诗    80
	张巧玲    60
	Name: android, dtype: int64
	修改单个值===========================
	'''
	# 4  修改值 新增列 新增行
	print("4  修改值 新增列 新增行")
	df0['android']['张伊曼'] = 100
	print(df0)

	print("修改一列值===========================")
	df0['android'] = [100, 100, 100]
	print(df0)

	print("新增列===========================")
	df0['c++'] = np.nan
	print(df0)

	print("新增行===========================")
	df0.ix['思思'] = np.nan
	print(df0)
	'''
	4  修改值 新增列 新增行
	     android  java  python   c
	张伊曼      100    99      98  80
	张诗诗       80    78      82  80
	张巧玲       60    89      85  80
	修改一列值===========================
	     android  java  python   c
	张伊曼      100    99      98  80
	张诗诗      100    78      82  80
	张巧玲      100    89      85  80
	新增列===========================
	     android  java  python   c  c++
	张伊曼      100    99      98  80  NaN
	张诗诗      100    78      82  80  NaN
	张巧玲      100    89      85  80  NaN
	新增行===========================
	     android  java  python     c  c++
	张伊曼    100.0  99.0    98.0  80.0  NaN
	张诗诗    100.0  78.0    82.0  80.0  NaN
	张巧玲    100.0  89.0    85.0  80.0  NaN
	思思       NaN   NaN     NaN   NaN  NaN
	'''
	# 对datafram 元素的函数式修改
	data=np.arange(0,16).reshape(4,4)
	data=pd.DataFrame(data,columns=['0','1','2','3'])
	
	print(data)
	print("对0,1 列所有行元素")
	print(data.ix[:,['0','1']].apply(f))
	print(data)
	print("对0,1 行所有列元素")
	print(data.ix[[0,1],:].apply(f))
	print("对所有行,所有列元素")
	print(data.apply(f))
	print("对所有列,所有行元素")
	print(data.apply(f,axis = 1))
	'''
	    0   1   2   3
	0   0   1   2   3
	1   4   5   6   7
	2   8   9  10  11
	3  12  13  14  15
	对0,1 列所有行元素
	    0   1
	0  -1   0
	1   3   4
	2   7   8
	3  11  12
	    0   1   2   3
	0   0   1   2   3
	1   4   5   6   7
	2   8   9  10  11
	3  12  13  14  15
	对0,1 行所有列元素
	   0  1  2  3
	0 -1  0  1  2
	1  3  4  5  6
	对所有行,所有列元素
	    0   1   2   3
	0  -1   0   1   2
	1   3   4   5   6
	2   7   8   9  10
	3  11  12  13  14
	对所有列,所有行元素
	    0   1   2   3
	0  -1   0   1   2
	1   3   4   5   6
	2   7   8   9  10
	3  11  12  13  14
	'''
def f(x):
	    return x-1

panda 学习好链接
https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.DataFrame.loc.html

argparse 的使用
https://blog.youkuaiyun.com/u013946404/article/details/78188266

import argparse
def use_argparse():
	# 创建解析对象
	parser = argparse.ArgumentParser("test solicucu")
	'''
	ArgumentParser.add_argument(name or flags…[, action][, nargs][, const][, default][, type][, choices][, required][, help][, metavar][, dest])
	第一个值为name 或者和flag,默认为必选,-开头为可选
	nargs 表示参数的个数,+ 1个以上 * 0个或多个
	const 表示常量,
	default 没输入的时候,默认值
	type 数据类型,python的都可以
	help 帮助的时候,显示参数的作用
	metavar 显示在help 里面的别名
	dest 返回值的命名,存储在namespace的key,用来访问字段值,默认为flag个名
	'''
	parser.add_argument('integers',metavar="N",type=int,nargs='+',help='input integer')
	parser.add_argument("-n",'--name',type=str,help="input your name",default="hanjun")
	
	args = parser.parse_args("1 2 3 ".split())
	print(args)

	args = parser.parse_args("1 2 3 -n solicucu".split())
	print(args)

	args = parser.parse_args("1 2 3 --name solicucu".split())
	print(args)
	# 转化为字典
	dict_args = vars(args)
	print(dict_args)
	
	args = parser.parse_args(["-h"])
	print(args)
	-------------------------------------------------
	Namespace(integers=[1, 2, 3], name='hanjun')
	Namespace(integers=[1, 2, 3], name='solicucu')
	Namespace(integers=[1, 2, 3], name='solicucu')
	{'integers': [1, 2, 3], 'name': 'solicucu'}
	usage: test solicucu [-h] [-n NAME] N [N ...]
	
	positional arguments:
	  N                     input integer
	
	optional arguments:
	  -h, --help            show this help message and exit
	  -n NAME, --name NAME  input your name

对python 类实现__call__ 函数

class Entity:
	'''调用实体来改变实体的位置。'''
	def __init__(self, size, x, y):
		self.x, self.y = x, y
		self.size = size

	# 通过实现call 是的对象实例可以像函数一样使用参数改变自己的变量
	def __call__(self, x, y):
		'''改变实体的位置'''
		# 函数里面定义函数,tql
		def change(x,y):
			self.x, self.y = x, y
		change(x,y)

def use_call():
	e = Entity(1, 2, 3) #// 创建实例
	e(4, 5) # 实例可以象函数那样执行,并传入x y值,修改对象的x y 
	print(e.x,e.y)
use_call()
4 5
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值