python类函数重构 python 子类重写

python程序怎么重构

其实不只是python,各种语言都是这样。唯一的办法就是多写,然后不停的回头去看自己写的代码,不停的去重构。同时也要多读,现在网上太多开源的代码,去观摩,一点一点的积累。

在曹县等地区,都构建了全面的区域性战略布局,加强发展的系统性、市场前瞻性、产品创新能力,以专注、极致的服务理念,为客户提供成都做网站、成都网站制作、成都外贸网站建设 网站设计制作定制设计,公司网站建设,企业网站建设,品牌网站建设,全网营销推广,外贸网站制作,曹县网站建设费用合理。

python主函数怎么写

一般来说,Python程序员可能是这样写main()函数的:

"""Module docstring.

This serves as a long usage message.

"""import sysimport getoptdef main():

# parse command line options

try:

opts, args = getopt.getopt(sys.argv[1:], "h", ["help"]) except getopt.error, msg: print msg print "for help use --help"

sys.exit(2) # process options

for o, a in opts: if o in ("-h", "--help"): print __doc__

sys.exit(0) # process arguments

for arg in args:

process(arg) # process() is defined elsewhereif __name__ == "__main__":

main()1234567891011121314151617181920212223242526

Guido也承认之前自己写的main()函数也是类似的结构,但是这样写的灵活性还不够高,尤其是需要解析复杂的命令行选项时。为此,他向大家提出了几点建议。

添加可选的 argv 参数

首先,修改main()函数,使其接受一个可选参数 argv,支持在交互式shell中调用该函数:

def main(argv=None):

if argv is None:

argv = sys.argv # etc., replacing sys.argv with argv in the getopt() call.1234

这样做,我们就可以动态地提供 argv 的值,这比下面这样写更加的灵活:

def main(argv=sys.argv):

# etc.12

这是因为在调用函数时,sys.argv 的值可能会发生变化;可选参数的默认值都是在定义main()函数时,就已经计算好的。

但是现在sys.exit()函数调用会产生问题:当main()函数调用sys.exit()时,交互式解释器就会推出!解决办法是让main()函数的返回值指示退出状态(exit status)。因此,最后面的那行代码就变成了这样:

if __name__ == "__main__":

sys.exit(main())12

并且,main()函数中的sys.exit(n)调用全部变成return n。

定义一个Usage()异常

另一个改进之处,就是定义一个Usage()异常,可以在main()函数最后的except子句捕捉该异常:

import sysimport getoptclass Usage(Exception):

def __init__(self, msg):

self.msg = msgdef main(argv=None):

if argv is None:

argv = sys.argv try: try:

opts, args = getopt.getopt(argv[1:], "h", ["help"]) except getopt.error, msg: raise Usage(msg) # more code, unchanged

except Usage, err: print sys.stderr, err.msg print sys.stderr, "for help use --help"

return 2if __name__ == "__main__":

sys.exit(main())123456789101112131415161718192021222324

这样main()函数就只有一个退出点(exit)了,这比之前两个退出点的做法要好。而且,参数解析重构起来也更容易:在辅助函数中引发Usage的问题不大,但是使用return 2却要求仔细处理返回值传递的问题。

8 Metaheuristics

下图介绍了两种不同种类的Metaheuristics,我们主要用左边的,尤其是Iterated Greedy。

I 和D 的过程用图像表示如下:

我在这里只用Iterated Greedy算法。原因如下:

其他算法诸如蚁群算法等,可能能提供非常接近最优解的方案,有些算法的运行速度也很快,可以弥补python运行慢的缺陷。但是这些算法通常存在诸多不足,例如算法太复杂,适用面很窄,需要设置过多参数导致很难实现。

Iterated Greedy的优势在于,它由两个简单的阶段构成:

D和I

更好的解决方案总会被接受

更坏的方案以特定的可能性接受,接受的概率如下图

类似 模拟退火法 :

从当前解决方案中随机删除 numberJobsToRemove 个订单。这里 numberJobsToRemove 是Iterated Greedy的一个参数。

输出的结果是被移除的订单集合 removedJobs 和一个不完整的解决方案 partialPermutation 。

* 注意:solver.RNG.choice的结果每次都一样,是因为我们设置了随机数种子,目的就是只要是用同一个种子作为参数构造出的solver的属性RNG都是同一个。

将 removedJobs 重新加回 partialPermutation ,并插入到最佳位置(NEH)的顺序,并返回新的完整解决方案。这个插入过程是通过排列Permutation实现的,看一下Construction函数的参数表可知,需要两个列表。

* 注:前面讲算法的时候说过,重构函数执行之后会生成一个新的方案newSolution,新方案就是通过把removedJobs插入到最佳位置得到的。最优位置的选择需要在Construction函数中借助 solver.EvaluationLogic.DetermineBestInsertion(completeSolution, i)来实现

我们通过简单的解构和重构,必然会得出一个新方案newSolution,那么我们接受新方案newSolution为当前方案currentSolution的前提是,如果

- 新的解决方案( newSolution ),

- 当前解决方案( currentSolution )。

* 公式中,T叫做baseTemperature,是Iterated Greedy的第二个参数,T越大,则接受更坏方案的概率也越大。新的最优方案存储在SolutionPool中(numberJobsToRemove是第一个参数)

下面开始对newSolution进行评估和比较:

* 注意:判断一个新方案是否可接受取决于两方面:1. 如果新方案更好,那么无论如何都会接受新方案;2. 如果新方案并没有优化,则视作WorseSolution,即使是worseSolution也是要按照公式计算出的概率来衡量是否要接受这个不好的方案

为了看起来更加直观,我把接受差方案的过程写成了函数AcceptWorseSolution。注意看参数表,以便于确定何时调用这个函数。

局部搜索可以被用于优化currentSOlution,但不是必须的。通常会使用IterativeImprovement结合Insertion邻域一起使用。

Iterated Greedy是一个迭代的解构D和构建C组成的序列。

在一个循环中被反复执行,直到达到 停止标准 。

在这里的例子中, 停止标准 是迭代次数 maxIterations ,但时间限制或没有优化的迭代次数也是可以的。

后面可能还会讲到怎么设计一个没有优化的迭代次数,这里可以先思考一下。

现在尝试运行一下:

与 IterativeImprovement 算法类似,现在要为 IteratedGreedy 创建一个单独的类,以便该类的一个实例可以传递给求解器Solver。

像 IterativeImprovement 一样, Iterated Greedy 应该继承自 ImprovementAlgorithm 。

必要的 参数 是以下属性:

EvaluationLogic, SolutionPool以及随机数生成器RNG都由求解器solver传递给算法。

添加 IteratedGreedy 类,以便它可以作为一种算法传递给求解器。

成员函数:Konstruktor, Initialize, Destruction, Construction, AcceptWorseSolution, Run

python重命名无法执行重构是为什么

语法错误。

这可能是由于Python脚本本身不在C:/test/temp中造成的。Python将在运行它的目录中查找文件名,这意味着它将尝试重命名不存在的文件。您必须在文件名中添加目标前缀。

重命名是指给文件或文件夹等重新起一个名称。


名称栏目:python类函数重构 python 子类重写
文章地址:http://pwwzsj.com/article/hjhjhc.html