当前位置:   article > 正文

【python VS vba】(1) python和vba读写文本文件的方式比较_python vba

python vba

目录

1 前言 : 为什么要做这个系列

2 用VBA 实现 遍历文件夹,读取文件内容,写入文件内容等

2.1 打开文件+遍历文件夹的文件名

2.1.1 做事之前先梳理一遍思路

2.1.2 用VBA取得文件名等需要使用 dir mkdir 等类dos的命令

测试这些函数和语句

2.1.3 DIR() 函数的用法

2.1.4 用open语句 打开,close语句 关闭文件:

2.1.5 代码例子1

2.1.5.1 打开文件夹,把文件夹内的文件名,输出到另外一个txt文件内

2.1.5.2 下面是运行的效果

2.1.6 代码例子2

2.2 如何读写:读取文件夹内所有文件内容到指定文件

2.2.1 基本的读取方式 

input语句

input() 函数

对应代码:可看出,input 和  line input语句效果一样,匪夷所思

对应代码:可看出,input() 函数可实现读取指定长度的内容

2.2.2 写入方式

2.3  代码例子:读取文件夹下多个文件内容

2.3.1 读取文件夹下多个文件内容

2.3.2 代码

2.3.3 相关函数和语句

2.4  向(已有)文件夹内的多个已有的多个文件写入

2.4.1 代码

2.5   向新建文件夹内的新文件输出

2.5.1 代码

2.6  向新建文件夹内的新文件输出(先判断是否存在此文件夹)

2.6.1 代码

3 VBA 其他操作文件方法,比如fso的简要了解(未完善,需要整理)

3.1 基础语法

3.2 读文件

3.3 写入文件

3.4  代码如下(逐行读取,逐行写入)

3.5 还可以简单粗暴的一次性读出,写入

3.6  也可以读取文件夹内容

3.7   fso的一些关键语法

3.8 使用fso 如何统计 某种后缀名类型的文件数量

4 用python 读取文件

4.1 我从之前我写的一个解题的代码里弄出一段代码

4.2 函数和语法

4.2.1 导入模块 os

4.2.2  使用地址path找到文件

4.3  打开文件

4.3.1  打开文件方式1:使用 open() 函数打开,file=open()

4.3.2 打开文件方式2: 使用with语句+打开, 就是 with + 文件对象

4.3.3 验证 open() 函数的返回值

4.4 关闭文件 file.close() 函数

4.5 读文件内容

4.5.1  读入内容方法1, file.read()整体读入

4.5.2 读入内容方法1, file.readlines()整体读入,并且直接返回的是列表

4.5.3  读入内容方法3:  for line in file 逐行读入

4.5.4 读入内容方法4: file.readline()逐行读入

4.5.5 关于指针函数seek

4.6  代码例子1:读写文件

4.7 代码例子2:读写文件

4.8 往文件内写入内容

5  VBA 和python 打开文本文件的比较

5.1 VBA处理文件方法总结

5.1.1 文件处理方法1: 函数式编程

5.1.2 也有对象的方法 FSO

5.2 py处理文本文件的方法总结

5.3 比较 VBA 和 python 文件处理的相关代码差别

5.3.1 VBA的内嵌EXCEL天生优势   VS python的各种import模块

5.3.2 VBA里还有很多语句式的命令,python里基本都是函数了

5.3.3 易用性的问题

5.3.4 简洁,方便来看


1 前言 : 为什么要做这个系列

放在第一篇需要先明确下目的

为什么要做这个系列

  • 1 我现在再看之前写的一些VBA或python的学习笔记,有点惨不忍睹的,虽然有些文章还算有用,尤其是解决具体问题的那种,但是那种学习总结的往往很多问题,虽然只要被有些同学顶起来收藏和点赞,我发现了都会尽量改,但总是感觉一言难尽
  • 2 市面上很少有做 python 和VBA对比的,尤其是深入进去每个模块功能进行对比的。原因大概是这几个:VBA太老太弱,python太火太强,真正科班出身的同学很少有看得起VBA的。但是VBA因为附着在EXCEL上,有着强大的生命力,办公人群(多数人不会代码)用的很多,还是需要有人有用VBA的需求,毕竟环境已经集成在office上了。
  • 3 做对比,比较下两种语言的处理方式,也可以比较感性的认识下,后出的语言的牛逼之处在哪,之前写VBA的各种老思路需要更新。
  • 4 做对比,也算是对VBA做个总结吧,听说EXCEL都已经支持python了...

2 用VBA 实现 遍历文件夹,读取文件内容,写入文件内容等

  • 现有文件夹如下
  • 想遍历文件夹里的文件名,文件内容,然后写入其他文件夹
  • 下面是具体的步骤

2.1 打开文件+遍历文件夹的文件名

2.1.1 做事之前先梳理一遍思路

  • 要读写文件,首先要能根据文件位置找到文件,找到文件地址即可
  1. 如果是文件夹内的多个文件又该怎么办?  dir(path)+ 循环多次dir() 可以取得文件夹内的文件名
  2. 如果文件不存在又该怎么办?创建呗,用mkdir
  • 文件地址怎么写?
  1. 用相对地址,默认是同一个文件夹内的
  2. 直接用绝对地址
  • 怎么打开文件呢
  1. 知道了地址怎么打开文件呢?用 open path for output as #1

2.1.2 用VBA取得文件名等需要使用 dir mkdir 等类dos的命令

文件操作函数或者语句,类DOS

  • dir:   dir(path1)   和 继续 dir()
  • mkdir:MkDir (path1)  创建文件/文件夹
  • CurDir :CurDir() 函数
  • ChDir :ChDir path 语句
  • ChDrive: 语句
测试这些函数和语句
  1. Sub testp1()
  2. Debug.Print CurDir()
  3. Debug.Print Dir("C:\Users\Administrator\Desktop\ptest1.txt")
  4. ChDir "d:\123"
  5. Debug.Print CurDir()
  6. ChDrive "d:\"
  7. Debug.Print CurDir()
  8. ChDrive "c:\"
  9. Debug.Print CurDir()
  10. ChDir "C:\Users\Administrator\Desktop"
  11. Debug.Print CurDir()
  12. End Sub

2.1.3 DIR() 函数的用法

  • 'dir() 后面只能用dir(),不能 Dir(path)否则会重置,重新开始从第一个文件名开始输出
  • 'dir获得是文件名,(包含文件名=后缀)像这种  ppp1.txt,但是不包含完整路径
  • '循环dir,会导致ppp1 ppp10 ppp2.txt这种文件名排序,需要注意不是按数字排序的
  • '文件如果没有会自动创建
  • 有个问题:chdir如果和当前目录相比已经跨盘符了,必须要先chdirve 后才行,否则切换不过去

总结dir()的特点

  • 参数
  • dir(path=文件路径)  ,可以直接返回文件名,返回文件名.后缀
  • dir(path=文件夹路径)  其中参数path 可以是文件夹,必须有\*.*这一级,否则取不到文件夹内的内容返回文件夹内的第一个文件名.后缀
  • 比如fp = "C:\Users\Administrator\Desktop\ppp\*.txt"

  • dir()   也可以不带参数的,但是需要配合 dir(path文件夹) 使用,dir(path)  配合 dir() 使用
  • 会接着显示当前文件夹当前指针后面的文件名,可以逐个显示文件夹内的文件名,但是排序是 1.txt 10.xtxt 2.txt  这样的次序

  • 返回值
  • dir(path)  的返回值,一定是文件名.后缀格式名(非绝对路径)

2.1.4 用open语句 打开,close语句 关闭文件:

  • 打开文件:open path for input as #别名
  • 关闭文件:   close #别名

吐槽:open path for mode  as # 居然没有一个支持既可读又可写的模式。。。。不可想象,要想又读又写,只能分开!

官方解释

Open pathname For mode [Access access] [lock] As [#] filenumber [Len = reclength]

参数:

1)pathname 必填。 指定文件名的字符串表达式,可包括目录或文件夹和驱动器。

2)mode 必填。 指定文件模式的关键字:Append、Binary、Input、Output 或 Random。 如果未指定,则以 Random 访问模式打开文件。

  1. Input:以输入方式打开,即读取方式。
  2. Output:以输出方式打开,即写入方式。
  3. Append:以追加方式打开,即添加内容到文件末尾。
  4. Binary:以二进制方式打开。
  5. Random:以随机方式打开,如果未指定方式,则以 Random 方式打开文件。

3)access 可选。 指定可对打开的文件执行的操作的关键字:Read、Write 或 Read Write。

4)lock 可选。 指定由其他进程限制在打开的文件上的操作的关键字:共享、锁定读取、锁定写入和锁定读写。

5)filenumber 必填。 一个有效文件号,范围为1到511(含1和511)。 使用FreeFile 函数可获取下一个可用的文件编号。

6)reclength 可选。 小于或等于 32,767(字节)的数。 对于以随机访问模式打开的文件,此值为记录长度。 对于序列文件,此值为缓冲的字符数。

  1. 如果pathname指定的文件不存在,那么在以 Append、Binary、Output 或 Random 模式打开文件时,即会创建它。

  2. 如果文件已由另一个进程打开,并且不允许指定的访问类型,则打开操作将失败,并将发生错误。

  3. 如果mode为Binary,则忽略Len子句。

  4. 在Binary,Input,Random模式中,你可以使用不同的文件号打开文件,而无需先关闭文件。 在 Append 和 Output 模式中,必须先关闭该文件,然后才能用不同文件号打开它。

2.1.5 代码例子1

2.1.5.1 打开文件夹,把文件夹内的文件名,输出到另外一个txt文件内
  1. '指定读取文件夹的路径内的 多个文字名字
  2. Sub print1001()
  3. '指定输出路径
  4. path1 = "C:\Users\Administrator\Desktop\ptest1.txt"
  5. fp = "C:\Users\Administrator\Desktop\ppp\*.*"
  6. fn = Dir(fp)
  7. '打印文件夹内的文件名
  8. Do While fn <> ""
  9. 'VBE调试窗口输出
  10. Debug.Print fn
  11. '向文件输出
  12. Open path1 For Append As #2
  13. Print #2, fn
  14. Close #2
  15. fn = Dir
  16. Loop
  17. Debug.Print "文件夹内的文件名已经遍历完毕,并且已经追加写入了" & path1 & "内"
  18. MsgBox ("文件夹内的文件名已经遍历完毕,并且已经追加写入了" & path1 & "内")
  19. End Sub
  20. 'dir总结
  21. '总结1:'dir 后面只能用dir,不能 Dir(fp)否则会重置会第一个文件名
  22. '总结2:'dir获得是文件名,(包含文件名=后缀)像这种 ppp1.txt,但是不包含完整路径
  23. '总结3:循环dir,会导致ppp1 ppp10 ppp2.txt这种文件名排序,需要注意不是按数字排序的
  24. '总结4:'文件如果没有会自动创建, output, input
  25. 'Append、Binary、Input、Output 或 Random。 如果未指定,则以 Random 访问模式打开文件。
  26. '打开文件:open 完整路径 for input/output/append as #别名
  27. '关闭文件:close #别名
  28. '写入文件内容: print

2.1.5.2 下面是运行的效果

2.1.6 代码例子2

  • 和上面的稍微有改写
  • 比如fp = "C:\Users\Administrator\Desktop\ppp\*.txt" ,可以利用*.* 改写为*.txt 筛选某一类文件,而不是全部文件。
  1. Sub test205()
  2. '指定输出路径
  3. path1 = "C:\Users\Administrator\Desktop\ptest1.txt"
  4. fp = "C:\Users\Administrator\Desktop\ppp\*.txt" '必须有\*.*这一级,否则取不到文件夹内的内容
  5. fn = Dir(fp)
  6. Open path1 For Output As #2
  7. '打印文件夹内的文件名
  8. Do While fn <> ""
  9. 'VBE调试窗口输出
  10. Debug.Print fn
  11. '向文件输出
  12. Print #2, fn
  13. fn = Dir
  14. Loop
  15. Close #2
  16. End Sub

2.2 如何读写:读取文件夹内所有文件内容到指定文件

可以参考我自己之前写的一篇文章

VBA小模板:如何把 txt / json /xml 文件内容读入到excel 表里_vba读取xml文件_奔跑的犀牛先生的博客-CSDN博客文章浏览阅读1.5k次,点赞3次,收藏19次。如何把 txt / json /xml 文件内容读入到excel 表里_vba读取xml文件https://blog.csdn.net/xuemanqianshan/article/details/129712309?spm=1001.2014.3001.5501

 line input可直接识别line input不可识别
但是可以通过split()分行
 
 文件分多行文件分多行文件内未分行
input只能读到第1行只能读到第1行全部内容读成为1行
line input不可识别的多行全部内容读成为1行全部内容读成为1行全部内容读成为1行
line input可识别的多行读成为多行全部内容读成为1行全部内容读成为1行
line input+split()可处理的多行读成为多行读成为多行全部内容读成为1行

2.2.1 基本的读取方式 

要读到文件夹内容

input语句
  • 这2个居然效果一样,都是读取文件内容的一行,但是实际上有差别。。。。
  • input 语句    Input #1, s
  • line input 语句  Line Input #1, s
  • line input + split() 处理分隔为行
input() 函数
  • input() 函数,指定读多少数量的内容
  • LOF(1), 指定多少长度的内容,比如lof(1) -100 ,就是去掉最后100个字符的内容
  • input(LOF(1), #1) 

对应代码:可看出,input 和  line input语句效果一样,匪夷所思
  1. Sub test206()
  2. '指定输出路径
  3. path1 = "C:\Users\Administrator\Desktop\ptest1.txt"
  4. Open path1 For Input As #2
  5. '打印文件夹内的文件名
  6. Do While Not EOF(2)
  7. '从文件内读入
  8. Input #2, curr1
  9. Debug.Print "Input #2, curr1=" & curr1
  10. Line Input #2, curr1
  11. Debug.Print "Line Input #2, curr1=" & curr1
  12. Loop
  13. Close #2
  14. End Sub

对应代码:可看出,input() 函数可实现读取指定长度的内容
  1. Sub test207()
  2. '指定输出路径
  3. path1 = "C:\Users\Administrator\Desktop\ptest1.txt"
  4. Open path1 For Input As #2
  5. '打印文件夹内的文件名
  6. Do While Not EOF(2)
  7. '从文件内读入
  8. curr1 = Input(LOF(2), #2)
  9. Debug.Print " curr1 = input(LOF(2), #2)" & curr1
  10. Loop
  11. Close #2
  12. End Sub

 2.2.1.1 line input + split() 处理分隔为行
  • line input + split() 处理分隔为行

例子

  1. Sub test2207() '尝试把文件内容已经分行,但是line input 无法直接识别的内容,变为分行后读入
  2. Dim sh1 As Object
  3. fnum = FreeFile
  4. Set sh1 = ThisWorkbook.Worksheets("a")
  5. m = 1
  6. Open "C:\Users\Administrator\Desktop\k\62" For Input As #fnum
  7. Do While Not EOF(fnum)
  8. Line Input #fnum, aaa1
  9. lll1 = Split(aaa1, Chr(10)) 'split()返回一个数组,以chr(10)为间隔分行
  10. ' For i = 0 To UBound(lll1) Step 1 'split()返回一个数组,index从0开始,千万别写成1,会少1个数据
  11. For i = LBound(lll1) To UBound(lll1) Step 1
  12. Debug.Print lll1(i)
  13. sh1.Cells(m, 2) = lll1(i)
  14. m = m + 1
  15. Next
  16. Loop
  17. Debug.Print "test207结束"
  18. Close fnum
  19. End Sub

2.2.2 写入方式

写入文件内容的语句:

  • print 语句,Print #2, curr1 ,内容
  • write语句 ,Write #1, 888,输出内容会自带 "" 引号

函数

  • 好像没有对应函数

  1. Sub test208()
  2. '指定输出路径
  3. path1 = "C:\Users\Administrator\Desktop\ptest1.txt"
  4. Open path1 For Append As #2
  5. Print #2, "ok1"
  6. Print #2, "OK2"
  7. Write #2, "ok1"
  8. Write #2, "ok1" & "OK2"
  9. ' Print (#2,"你好")
  10. ' write (#2,"你好")
  11. Close #2
  12. End Sub

2.3  代码例子:读取文件夹下多个文件内容

 

2.3.1 读取文件夹下多个文件内容

  • 要读取的文件,打开时用input即可
  1. 需要循环到文本结尾,读取全部内容
  2. 用eof(1)判断是否到文件结尾
  3. '用lof(别名文件号) 判断长度,可以直接 lof(1)-10 取部分内容
  • 要写入的文件,使用append
  1. 每次找循环里的下一个文件 path3 = path2 & "\" & fn  (有些语言需要注意windows的文件符号\相反的问题)
  2. input函数(长度,别名)
  3. '需要input函数,可用变量暂存内容=input(长度,别名)
  4. 用中间变量,倒一下内容
  5.             curr1 = input(LOF(1), #1)
                Print #2, curr1

2.3.2 代码

  1. '读取文件夹内的每个文件内容到另外一个指定的txt里
  2. Sub print1002()
  3. '指定输出路径
  4. path1 = "C:\Users\Administrator\Desktop\ptest1.txt"
  5. '指定读取文件夹的路径
  6. fp = "C:\Users\Administrator\Desktop\ppp\*.*"
  7. fn = Dir(fp)
  8. path2 = "C:\Users\Administrator\Desktop\ppp"
  9. '打印文件夹内的文件名
  10. Open path1 For Append As #2
  11. Do While fn <> ""
  12. 'VBE调试窗口输出
  13. Debug.Print fn
  14. '向文件输出
  15. path3 = path2 & "\" & fn
  16. Open path3 For Input As #1
  17. Do While Not EOF(1)
  18. curr1 = input(LOF(1), #1)
  19. Print #2, curr1
  20. Loop
  21. Close #1
  22. fn = Dir
  23. Loop
  24. Close #2
  25. End Sub
  26. '读取文件,打开时用input即可
  27. '用lof(别名文件号) 判断长度,可以直接 lof(1)-10 取部分内容
  28. '用eof(1)判断是否到文件结尾
  29. '需要input函数,可用变量暂存内容=input(长度,别名)

2.3.3 相关函数和语句

Input() 函数

  1. input函数,input(长度,别名)
  2. Input #1, MyString, MyNumber ' 将数据读入两个变量。

Input() 语句

  1. 语法:Input #filenumber, varlist
  2. 功能:从已打开的顺序文件中读出数据并将数据指定给变量。
  3. 说明:通常用 Write # 将 Input # 语句读出的数据写入文件。为了能够用 Input # 语句将文件的数据正确读入到变量中,在将数据写入文件时,要使用 Write # 语句而不使用 Print # 语句。使用 Write # 语句可以确保将各个单独的数据域正确分隔开。

EOF 函数

  1. 语法:EOF(filenumber)
  2. 功能:返回一个 Integer,它包含 Boolean 值 True,表明已经到达为 Random 或顺序 Input 打开的文件的结尾。

LOF 函数

  1. 语法:LOF(filenumber)
  2. 功能:返回一个 Long,表示用 Open 语句打开的文件的大小,该大小以字节为单位。

Loc 函数

  1. 语法:LOc(filenumber)
  2. 功能:返回一个 Long,在已打开的文件中指定当前读/写位置

2.4  向(已有)文件夹内的多个已有的多个文件写入

  • 目标:已有文件夹内的所有文件
  • 发现几个文件写入几个文件,全部覆盖
  • 写入内容,用print 语句写入

2.4.1 代码

  1. '向文件夹内的多个文件输出内容,已有的多个文件,发现几个文件写入几个文件
  2. Sub print1003()
  3. path1 = "C:\Users\Administrator\Desktop\ppp1"
  4. fp1 = "C:\Users\Administrator\Desktop\ppp1\*.*"
  5. fn1 = Dir(fp1)
  6. x = 1
  7. Do While fn1 <> ""
  8. path2 = path1 & "\" & fn1
  9. '向文件输出
  10. Open path2 For Output As #1
  11. Print #1, x & "第" & x & "句内容XXX"
  12. Close #1
  13. x = x + 1
  14. fn1 = Dir
  15. Loop
  16. End Sub

2.5   向新建文件夹内的新文件输出

  • 目标:一般针对新文件夹,重新创建文件夹和新文件
  • 指定要输出到文件夹里的文件个数,
  •  为这些新文件写入内容

2.5.1 代码

  1. '指定要输出到文件夹里的文件个数,一般针对新文件夹,重新创建文件夹和新文件
  2. Sub print1004()
  3. '如果已有文件夹里有其他文件夹应该会忽略掉
  4. path2 = "C:\Users\Administrator\Desktop\ppp2"
  5. y = 1
  6. For i = 1 To 10
  7. path6 = path2 & "\" & i & ".txt"
  8. '向文件输出
  9. Open path6 For Output As #1
  10. Print #1, y & "第" & y & "句内容YYYYY"
  11. Close #1
  12. y = y + 1
  13. Next
  14. End Sub

2.6  向新建文件夹内的新文件输出(先判断是否存在此文件夹)

  •  目标:严谨的输出到新文件夹内,严谨点先判断是否是空文件夹
  • 指定要输出到文件夹里的文件个数

2.6.1 代码

  1. '指定要输出到文件夹里的文件个数,严谨点先判断是否是空文件夹
  2. Sub print1005()
  3. path1 = "C:\Users\Administrator\Desktop\ppp3"
  4. '先判断文件夹是否存在
  5. If Dir(path1) <> "" Then
  6. ' MsgBox ("请注意此文件夹已存在,里面可能已经包含其他文件",vbYesNo)
  7. MsgBox ("请注意此文件夹已存在,里面可能已经包含其他文件")
  8. Else
  9. MkDir (path1)
  10. End If
  11. Z = 1
  12. '因为确定了是新文件夹,肯定是空文件夹了
  13. For i = 1 To 10
  14. path7 = path1 & "\" & i & ".txt"
  15. '向文件输出
  16. Open path7 For Output As #1
  17. Print #1, Z & "第" & Z & "句内容ZZZZ"
  18. Close #1
  19. Z = Z + 1
  20. Next
  21. End Sub


3 VBA 其他操作文件方法,比如fso的简要了解(未完善,需要整理)

3.1 基础语法

3.2 读文件

  • readtext = f1.readline
  • readtext = f1.readall

Set fso = CreateObject("scripting.filesystemobject")
Set f1 = fso.opentextfile(filepath1, 1, True)
Do Until f1.AtEndOfLine

        readtext = f1.readline

  • 1 判断文件结尾   Do Until f1.AtEndOfLine
  • 2 逐行读入内容,可以暂存入变量,readtext = f1.readline

readtext = f1.readall
f2.write (readtext)

  • 一次性读入也可以
  • 也可以一次性写入

3.3 写入文件

  • f2.write (readtext)
  • f2.writeline (readtext)

Set fso = CreateObject("scripting.filesystemobject")
Set f2 = fso.opentextfile(filepath2, 2, True)
f2.writeline (readtext)

  • fso.opentextfile(filepath2, 2, True)
  • 参数1:文件路径
  • 参数2:文件模式,1读,2写
  • 参数3:

3.4  代码如下(逐行读取,逐行写入)

  1. Sub test202()
  2. Dim fso As Object
  3. Dim f1
  4. Dim filepath1
  5. Dim i
  6. filepath1 = "C:\Users\Administrator\Desktop\wateranswer.txt"
  7. filepath2 = "C:\Users\Administrator\Desktop\111.txt"
  8. Set fso = CreateObject("scripting.filesystemobject")
  9. Set f1 = fso.opentextfile(filepath1, , , tristate = 1)
  10. Set f2 = fso.opentextfile(filepath2, 2, True)
  11. i = 1
  12. readtext = ""
  13. Do Until f1.AtEndOfLine
  14. readtext = f1.readline
  15. Debug.Print readtext
  16. ThisWorkbook.Worksheets("sheet1").Cells(i, 1).Value = readtext
  17. f2.writeline (readtext)
  18. i = i + 1
  19. Loop
  20. Debug.Print "读取完成"
  21. End Sub

3.5 还可以简单粗暴的一次性读出,写入

  • 这种简单粗暴,只适合文本文件,不适合EXCEL等表格格式内容

readtext = f1.readall
f2.write (readtext)

  • 方法
  • fso.readall 即可
  • 也不用循环了,也不要判断到文档结尾了
  1. Sub test203()
  2. Dim fso As Object
  3. Dim f1
  4. Dim filepath1
  5. Dim i
  6. filepath1 = "C:\Users\Administrator\Desktop\wateranswer.txt"
  7. filepath2 = "C:\Users\Administrator\Desktop\111.txt"
  8. Set fso = CreateObject("scripting.filesystemobject")
  9. Set f1 = fso.opentextfile(filepath1, , , tristate = 1)
  10. Set f2 = fso.opentextfile(filepath2, 2, True)
  11. readtext = f1.readall
  12. Debug.Print readtext
  13. f2.write (readtext)
  14. Debug.Print "读取完成"
  15. End Sub

3.6  也可以读取文件夹内容

  1. Sub test204()
  2. Dim fso
  3. Dim f1
  4. 'fso对象可以返回文件夹名或者文件名,但是打开文件夹需要用fso.getfolder()方法fso.opentextfile()不同
  5. Set fso = CreateObject("scripting.filesystemobject")
  6. Set f1 = fso.getfolder("C:\Users\Administrator\Desktop\ppp")
  7. Debug.Print f1
  8. Debug.Print f1.Name
  9. Debug.Print f1.Files.Count
  10. 'dir 只能返回文件的名字,不能返回文件夹名字
  11. f2 = Dir("C:\Users\Administrator\Desktop\ppp")
  12. Debug.Print f2
  13. 'Debug.Print f2.Name 'f1是fso对象,但是f2不是,f2只是1个变量
  14. f3 = Dir("C:\Users\Administrator\Desktop\ppp\ppp1.txt")
  15. Debug.Print f3
  16. End Sub
  • dir(文件名) 可以返回 文件名
  • dir(文件夹) 返回空,不能返回文件夹名字,但是不报错
  • dir(文件名) 不是对象

  • fso对象,可以取对象属性,如 fso.name
  • 'fso对象可以返回文件夹名或者文件名
  • 打开文件夹方法:fso.getfolder()
  • 打开文件方法:    fso.opentextfile()

3.7   fso的一些关键语法

fso的属性

  • f1.AtEndOfLine
  • f1.name
  • AtEndOfLine: 文件指针正好在行尾标记,则返回TRUE
  • AtEndOfStream: 文件指针在文件末尾,则返回TRUE
  • Line: 返回一个 TextStream 文件中的当前行号。
  • Column: 返回 TextStream 文件中当前字符位置的列号。
  • write 语句     
  • writeline  
  • fso.write      不能这样空行       
  • fso.writeline         
  • 没有这样的方法  fso.print          
  • f.close        (见上面)
  • f.write         (见上面)
  • f.writeline    (见上面)
  • f.read
  • f.readall
  • f.readline
  • f.skipline       光标跳到下一行
  • f.skip   5        光标往后跳几个字节
  • line input 语句
  • all input ?
  • readall
  • readline

3.8 使用fso 如何统计 某种后缀名类型的文件数量

  1. Sub jackma101()
  2. Dim path1
  3. path1 = "C:\Users\Administrator\Desktop\test1"
  4. Call ponyma101(path1)
  5. End Sub
  6. Function ponyma101(path1)
  7. ' 先查某类型的文件数量
  8. Dim fso As Object
  9. Dim fd1 As Object
  10. Dim f1 As Object
  11. Set fso = CreateObject("scripting.filesystemobject")
  12. Set fd1 = fso.getfolder(path1)
  13. x1 = fd1.Files.Count
  14. Debug.Print "所有文件数为:" & x1
  15. For Each f1 In fd1.Files
  16. If fso.getextensionname(path1 & "\" & f1.Name) = "txt" Then
  17. ' fso.getfile(path1).getextensionname
  18. ' f1.getextensionname
  19. '只有一种语法可这么用
  20. y1 = y1 + 1
  21. End If
  22. Next
  23. Debug.Print ".txt文件数为:" & y1
  24. End Function

  1. Sub jackma101()
  2. Dim path1
  3. path1 = "C:\Users\Administrator\Desktop\test1"
  4. Call ponyma101(path1)
  5. End Sub
  6. Function ponyma101(path1)
  7. ' 先查某类型的文件数量
  8. Dim fso As Object
  9. Dim fd1 As Object
  10. Dim f1 As Object
  11. Set fso = CreateObject("scripting.filesystemobject")
  12. Set fd1 = fso.getfolder(path1)
  13. x1 = fd1.Files.Count
  14. Debug.Print "所有文件数为:" & x1
  15. For Each f1 In fd1.Files
  16. If f1.Name Like "*.txt" Then
  17. '只有一种语法可这么用
  18. ' If fso.getextensionname(path1 & "\" & f1.Name) = "txt" Then
  19. ' fso.getfile(path1).getextensionname
  20. ' f1.getextensionname
  21. y1 = y1 + 1
  22. End If
  23. Next
  24. Debug.Print ".txt文件数为:" & y1
  25. End Function

3.9 如果用VBA判断文件/文件夹 路径是否存在

VBA

判断文件是否存在,文件夹是否存在,直接

  •  if  dir(path1)=""
  •  if  dir(path1)=vbNullString

 如果是fso这种对象

  • Set fso = CreateObject("Scripting.FileSystemObject")

  • If fso.folderExists(strFullPath) Then FileFolderExists = True

  • Set fso = Nothing

4 用python 读取文件

4.1 我从之前我写的一个解题的代码里弄出一段代码

  1. import copy
  2. import os
  3. import xlwt
  4. import openpyxl
  5. #中间省略了很多代码
  6. #从文件夹里逐个读文件,逐个判断,结果输出到EXCEL里
  7. test = Puzzle()
  8. folder_path=r"C:\Users\Administrator\Desktop\ppp"
  9. file_names = os.listdir(r"C:\Users\Administrator\Desktop\ppp")
  10. y=1
  11. with open(r"C:\Users\Administrator\Desktop\wateranswer.txt",'a') as f:
  12. # 遍历文件名列表,逐个读取文件内容
  13. for file_name in file_names:
  14. print(file_name)
  15. file_path = os.path.join(folder_path, file_name) # 应该会自动加\吧
  16. #if os.path.isfile(file_path):
  17. test.readfile(file_path)
  18. test.print()
  19. a = A_star(test)
  20. if a == None:
  21. print("None!")
  22. f.write("第%d题无解" %y) #组合参数字符串?
  23. f.write("\n")
  24. else:
  25. print("%d steps"%len(a[0]))
  26. print(a[0])
  27. a[1].print()
  28. f.write("第%d题有解" %y)
  29. f.write("%d steps"%len(a[0])+"\n")
  30. f.write(" ".join(str(x) for x in a[0])+"\n") #数组转字符串
  31. y=y+1

4.2 函数和语法

4.2.1 导入模块 os

  • import os
  • 导入专门进行文件处理的的os模块

4.2.2  使用地址path找到文件

  • 文件地址path
  • 但是注意:rawdata,需要加 r"...."

path1=r"C:\Users\Administrator\Desktop\ptest1.txt"

with open(path1,"a") as file2:

  • 直接取文件夹内的文本名---直接返回文件名列表!
  • file_names = os.listdir(r"C:\Users\Administrator\Desktop\ppp")  可以得到一个文件名的列表!
  • 直接就是列表,方便操作

  • 文件名连接
  • file_path = os.path.join(folder_path, file_name)  # 应该会自动加\吧

4.3  打开文件

  •  open(path,"a") 
  • 参数1:path
  • 参数2:mode 打开模式,比如现在填的"a" 即可 mode="a",表示 append模式,如果缺省,默认是read模式
  • 有兼容读写的模式:"r+","w+","a+"
  • 返回值: open(path,"a") 返回的是文件对象,可以复制给一个变量

r只读模式,打开一个文件用于读取。如果文件不存在,则会发生错误。
w写入模式,打开一个文件用于写入。如果文件已经存在,则清空文件内容;如果文件不存在,则创建新文件。
a追加模式,打开一个文件用于追加内容。如果文件不存在,则创建新文件。
x创建模式,创建一个新文件用于写入。如果文件已经存在,则会发生错误。
b二进制模式,用于读取或写入二进制数据。与其他模式配合使用,如rb、wb、ab等。
t文本模式,默认模式,用于读取或写入文本数据。与其他模式配合使用,如rt、wt、at等。
+读写模式,用于既能读取又能写入文件的操作。与其他模式配合使用,如r+、w+、a+等。

4.3.1  打开文件方式1:使用 open() 函数打开,file=open()

  • file=open(path1,"a") 
  • 错误 open(path1,"a") as file:

4.3.2 打开文件方式2: 使用with语句+打开, 就是 with + 文件对象

  • 正确  with open(path1,"a") as file2:

4.3.3 验证 open() 函数的返回值

file3=open(path1,"a")
print(file3)

可以看到会返回这样的一个对象
<_io.TextIOWrapper name='C:\\Users\\Administrator\\Desktop\\ptest1.txt' mode='a' encoding='cp936'>

4.4 关闭文件 file.close() 函数

  • 使用 with open() as f  不需要再关闭文件
  • 但是如果只 open打开,没有使用with则需要 file.close()

4.5 读文件内容

4.5.1  读入内容方法1, file.read()整体读入

  • file.read() 函数,整体读入文件内容

file3=open(path1,"a+")
file3.seek(0)
content1=file3.read()
print(content1)

4.5.2 读入内容方法1, file.readlines()整体读入,并且直接返回的是列表

  • file.readlines() 函数,整体读入文件内容
  • 返回内容是列表,可以直接切片操作
  • 比如下面这个取到的就是内容数组的0,1,2前3个内容

file3=open(path1,"a+")
file3.seek(0)
lines=file3.readlines()
print(lines)
print(lines[:3])

4.5.3  读入内容方法3:  for line in file 逐行读入

  • file 本身可以是一个 可迭代对象(列表?),天生按行分隔
  • 直接用 for line in file + print(line) 可以逐行读入
  • 但是这样每行之间都会空一行

file3=open(path1,"a+")
file3.seek(0)
for line in file3:
    print(line)

4.5.4 读入内容方法4: file.readline()逐行读入

  • 直接用 file3.readline() 可以逐行读入
  • 但是这样每行之间都会空一行
  • file3.readline(2)  还可以指定读入某行的几个字符,这里是前2个字符

file3=open(path1,"a+")
file3.seek(0)
for line in file3:
    print(line)

4.5.5 关于指针函数seek

  • file3.seek(0)
  • fileObject.seek(offset[, whence])
  • offset:表示开始的偏移量,也就是需要偏移的字节数。
  • whence为可选参数,默认值为0,表示要从哪个位置开始偏移。
  • 0代表将文件开头作为起点,1代表从当前位置开始算起,2代表从文 件末尾算起。

  • 为什么要用seek()
  • 因为使用 读写文件,包括read() ,for line in file ,甚至是write 写文件,都会修改文件的指针,如果要读文件全部内容,必须用seek(0) 进行复位

4.6  代码例子1:读写文件

  1. import os
  2. path1=r"C:\Users\Administrator\Desktop\ptest2.txt"
  3. path2=r"C:\Users\Administrator\Desktop\ppp"
  4. file_names=os.listdir(path2)
  5. #for file_name in file_names:
  6. #print(file_name)
  7. with open(path1,"a") as file2: # open必须连着 with open ?
  8. file2.write("新增一句")
  9. file2.write("\n")
  10. file3=open(path1,"a+")
  11. print(file3)
  12. file3.write("再新增一句")
  13. file3.write("\n")
  14. file3=open(path1,"a+")
  15. file3.seek(0)
  16. content1=file3.read()
  17. print(content1)
  18. file3=open(path1,"a+")
  19. file3.seek(0)
  20. for line in file3:
  21. print(line)
  22. file3=open(path1,"a+")
  23. file3.seek(0)
  24. print(file3.readline())
  25. print(file3.readline())
  26. print(file3.readline(2)) #只要这行的前2个字符
  27. file3=open(path1,"a+")
  28. file3.seek(0)
  29. lines=file3.readlines()
  30. print(lines)
  31. print(lines[:3])

4.7 代码例子2:读写文件

  • 使用with open ()  as 别名 打开文件
  • 使用write 往文件内写入内容 
  1. import os
  2. path1=r"C:\Users\Administrator\Desktop\ptest1.txt"
  3. path2=r"C:\Users\Administrator\Desktop\ppp"
  4. #file_names = os.listdir(path2) 
  5. file_names=os.listdir(path2)
  6. for file_name in file_names:
  7. print(file_name)
  8. with open(path1,"a") as file2: # open必须连着 with open ?
  9. file2.write("新增一句")
  10. file2.write("\n")

4.8 往文件内写入内容

  •  f.write("第%d题无解" %y)   
  •  f.write("\n")
  • write()写入的内容是一个字符串,如果不是,则需要提前转换。
  • f.write(str(a)) # 强制类型转换
     

5  VBA 和python 打开文本文件的比较

5.1 VBA处理文件方法总结

5.1.1 文件处理方法1: 函数式编程

  • 用dir() 读文件名,
  • 用 open () for  output as #1 取得文件
  • 用print写入,或者用=input 读入
  • 注意close

5.1.2 也有对象的方法 FSO

  • 需要set 对象
  • 其他流程类似

5.2 py处理文本文件的方法总结

  • 处理流程和VBA差不多
  • 处理逻辑差不多

  • file 一定是对象
  • 使用 file=open()  打开文件
  • 使用 file.write() 往文件内写入内容 

5.3 比较 VBA 和 python 文件处理的相关代码差别

5.3.1 VBA的内嵌EXCEL天生优势   VS python的各种import模块

  • 先撇开VBA的编辑器VBE内嵌在EXCEL里,处理EXCEL有近水楼台的效果,比较python和VBA处理一般文件,比如文本文件的差别。
  • python的方法,还是他各种各样的import的轮子,对比封闭的VBA,扩展性是无敌的

5.3.2 VBA里还有很多语句式的命令,python里基本都是函数了

  • VBA里有很多语句和函数并存,甚至语句为主,函数次之
  • 比如  input() 和 input  write 和 write()
  • 历史原因
  • 代码用的人少了
  • 只是office占用还很高,否则VBA早没了

5.3.3 易用性的问题

VBA

  • 吐槽:open path for mode  as # 居然没有一个支持既可读又可写的模式。。。。不可想象,要想又读又写,只能分开!

python

  • 兼容模式 python 可以用  open (path,r+) 等模式即可
  • file_names = os.listdir(r"C:\Users\Administrator\Desktop\ppp")  可以得到一个文件名的列表!直接就是列表,方便操作
  • lines=file.readlines()  可以直接返回一个列表!

5.3.4 简洁,方便来看

  • 优势在于,py语言本身的简洁,毕竟是新语言

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/你好赵伟/article/detail/596719
推荐阅读
相关标签
  

闽ICP备14008679号