可读性与可扩展性:一个完美的函数 #P010#

在这一篇文章中,我们会在os.walk函数的基础上,封装一个查找文件的函数。如果读者是一位编程经验还不太丰富的工程师,相信可以从这篇文章中受到一些启发,并在以后的工作中,更加能够编写出扩展性强、可读性强、好维护的代码。

1 使用os.walk遍历目录树

为了避免读者不了解os.walk函数,从而无法理解这篇文章在就讲什么。因此,在正式介绍今天的主题之前,我们先来看一下os.walk函数的使用。

os.walk函数用以查找某个目录下的文件和目录,相对于os.listdir,os.walk不但会列出当前目录下的文件和目录,还会递归地遍历目录下的子目录。例如,查找某个目录及其子目录下所有的图片文件。对于这个查找图片的需求,可以使用os.walk函数。os.walk函数遍历某个目录及其子目录,对于每一个目录,walk返回一个三元组(dirpath, dirnames, filenames)。其中,dirpath保存的是当前目录,dirnames是当前目录下的子目录列表,filenames是当前目录下的文件列表。

下面的代码演示了os.walk函数的用法,使用os.walk函数遍历lmx这个用户的HOME目录及其子目录,并找到所有的图片文件:

#!/usr/bin/python
#-*- coding: UTF-8 -*-
import os
import fnmatch

images = ['*.jpg', '*.jpeg', '*.png', '*.tif', '*.tiff']
matches = []

for root, dirnames, filenames in os.walk(os.path.expanduser("~lmx")):
    for extensions in images:
        for filename in fnmatch.filter(filenames, extensions):
            matches.append(os.path.join(root, filename))

print(matches)

在这段代码中,我们查找lmx这个用户的HOME目录及其子目录,然后通过fnmatch进行文件扩展名匹配。如果文件匹配了某一个扩展名,则会将该文件保存到结果列表(matches)中。

基于os.walk函数,我们还可以实现一个功能,那就是在遍历目录及其子目录时,如果想要忽略掉某一个子目录,可以直接修改三元组中的dirnames。即从dirnames这个列表中移除需要忽略掉的目录,就实现了查找文件时排除某个目录的目的。如下所示:

for root, dirnames, filenames in os.walk(os.path.expanduser("~lmx/t")):
	......

    if 'exclude_dir' in dirnames:
        dirnames.remove('exclude_dir')

2 封装成函数

在前面的例子中,我们演示了os.walk函数的用法。现在,大家都知道这段程序的作用,是找到某个目录下所有的图片文件。但是,假设读者没有阅读到前面的说明文字,仅仅是阅读了代码,是否能够快速地知道这段程序的作用呢?或者说,读者下次再来看这段代码,能否快速的知道这段代码的作用呢?

这就涉及到一个代码编程规范:在编程时,我们应该尽可能将代码封装到函数中,并为函数取一个顾名思义的名字,以提高程序的可读性。我们一起来尝试一下,为上面的代码取一个顾名思义的名字&#

设计一个定时器来控制P010次流水灯的周期性点亮和熄灭,通常会涉及到嵌入式系统或者微控制器编程,比如Arduino或Python的RPi.GPIO库。这里我们假设是在基于Arduino UNO平台的环境下,因为它的Timer1功能非常适合这种任务。 首先,你需要初始化Timer1,并设置一个1秒的定时周期。然后创建一个函数,当定时器溢出时,这个函数会被调用,用于切换流水灯的状态(开或关)。由于P01010个LED,可以使用数组来表示它们的状态。 以下是伪代码示例: ```cpp #include <TimerOne.h> const int LED_COUNT = 10; // 流水灯的数量 bool ledState[LED_COUNT]; // 初始化所有LED关闭 // 创建一个定时器中断处理函数 void timerInterrupt() { static int counter = 0; if (counter >= LED_COUNT) { // 完成一个循环后清零计数器 counter = 0; } // 切换LED状态 ledState[counter] = !ledState[counter]; // 更新LED状态 for (int i = 0; i < LED_COUNT; ++i) { digitalWrite(LED_PORT + i, ledState[i]); // LED PORT可能是P0 or P1等 } counter++; // 继续下一盏灯的切换 } void setup() { Timer1.initialize(); // 初始化Timer1 attachInterrupt(digitalPinToInterrupt(TIMER1_PIN), timerInterrupt, RISING); // 设置中断源和回调函数 Timer1.setMode(COUNT_UP, 83); // 设置模式为溢出,分频率为83(这取决于你的时钟频率) Timer1.write(65535 / LED_COUNT - 1); // 设置定时时间大约为1秒,具体数值取决于你的硬件和时钟频率 } void loop() {} ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值