大家好,今天来为大家解答如何获取漫画资源源码分享网站这个问题的一些问题点,包括漫画源码app也一样很多人还不知道,因此呢,今天就来为大家分析分析,现在让我们一起来看看吧!如果解决了您的问题,还望您关注下本站哦,谢谢~
仔细观察单词Radar、Kayak、Rotator和Sexes,它们有什么共同的特点呢?这些单词都是回文(Palindrome),无论是从前往后拼写,还是从后往前拼写,它们都构成同一个单词。回文短语在这方面表现得更加明显,整个短语正着拼写和倒着拼写都表达同样的意思。拿破仑就是一位著名的回文创造者。拿破仑曾被流放到厄尔巴岛,当第一次见到这个岛时他说道:“AblewasIereIsawElba.”
2011年,DC漫画公司出版了一本有趣的书,书中的某些故事情节就涉及回文。当超级英雄女巫萨塔娜受到诅咒时,她只能通过默念回文形式的咒语来施展法力。为了击败挥舞着剑的攻击者,女巫萨塔娜必须设法想出诸如“nursesrun”“stackcats”“puffup”之类的两字短语。这引发了我的思考:故事中的回文短语到底还有多少呢?女巫萨塔娜还有更好的选择吗?
在本章中,你会从网上获取字典文件,并把这些文件加载到程序中,再利用编写的Python程序寻找这些文件所包含的回文单词。接下来,你会学习从文件中寻找更为复杂的回文短语的方法。之后,你将尝试用一个叫作cProfile的工具分析程序代码的性能,该工具有助于你编写出性能更好的代码。最后,你会学习回文的筛选方法,看看它们中有多少个具有“攻击”性的含义。
2.1寻找和加载字典文件
本章中的所有项目均需要使用一个以文本格式存储的单词列表文件。通常,这种文件也被称为字典文件(DictionaryFile)。因此,在继续学习新内容之前,我们先来探讨一下加载字典文件的问题。
尽管我们称这样的文件为字典文件,但是字典文件中只包含单词本身,不包含单词的发音、音节数、含义等。这是一个好消息,倘若字典文件中包含单词的这些信息,那将阻碍我们进行本章的项目。对你来说,还有一个更好的消息,那就是这些字典文件可以免费从网上获取。
从本书配套资源给定的链接中可以找到适用于本章项目的字典文件。下载其中的一个文件,或者以在线的方式直接打开所选文件,复制其内容并粘贴到诸如Notepad、WordPad(macOS上的TextEdit)之类的文本编辑软件中,将其另存为.txt类型的文本文件。将字典文件和Python程序放在同一目录中。本章项目使用的文本文件名字是2of4brif.txt。该文件位于配套资源的压缩文件12dicts-6.0.2.zip中。
除了配套资源给出的文件外,UNIX和类UNIX操作系统中还附带一个含有200000多个单词的大型单词文件,并用换行符把这些单词分隔开。该文件通常存储于/usr/share/dict/words或者/usr/dict/words目录下。在DebianGNU/Linux操作系统上,该单词列表存储在/usr/share/opendict/dictionary目录下。在macOS上,字典文件通常存储在/Library/Dictionaries目录下,这个目录下还包含一些非英文的字典文件。若要使用这些字典文件,你需要根据操作系统及版本在线查找这些文件的准确存储位置。
有些字典文件不包含单词a和I;而在有些字典中,每个字母都可以作为一个单独的单词(例如,d就是字典文件中以字母d开头的首个单词)。在本书项目中,我们将忽略单个字母形式的回文。因此,刚刚提到的问题应该容易解决。
2.1.1处理文件打开异常
无论什么时候,当加载一个外部文件时,程序都会自动检查一些I/O问题,并告知你是否存在这样的问题,例如文件丢失或文件名错误。
使用下面的try和except语句来捕获和处理程序执行过程中某些错误引发的异常:
?try:\n?withopen(file)asin_file:\ndosomething\nexceptIOError?ase:\n?print(&34;.format(e,file),\nfile=sys.stderr)\n?sys.exit(1)
首先,执行try语句块?。该语句块内的with语句能够保证嵌套代码块无论以什么样的方式结束,文件都会被自动关闭?。在终止进程之前关闭已打开文件是一种很好的编程习惯。如果不关闭这些文件,可能会耗尽系统的文件描述符(长时间运行的大型脚本就容易出现这类问题)。在Windows操作系统中,若不关闭文件,系统就会锁定文件,造成文件无法被进一步访问。如果一直向这些文件中写入数据,会使文件损坏或者数据丢失。
如果出现错误,并且错误类型与except关键字之后命名的异常类型相匹配?,那么会跳过剩余的try语句,直接执行except语句块内的语句?。若没有出现错误,程序就只执行try语句块内的语句,同时跳过except语句块。except语句块中的print语句会让用户知道存在的问题是什么,而file=sys.stderr参数会将IDLE解释器窗口中的错误语句标红。
语句sys.exit(1)?用于终止程序。语句sys.exit(1)表示程序退出,参数1表明程序没有正常关闭。
若发生的异常与except语句指定的异常类型不匹配,则这个异常会被抛给任何外部try语句块或主程序。若不存在该类型异常的处理语句,则这个异常会导致程序终止,并发出标准的“traceback”错误提示消息。
2.1.2加载字典文件
清单2-1的功能是以列表的形式加载字典文件的内容。你既可以手动输入该脚本,也可以从本书配套资源中获取其对应的程序文件load_dictionary.py。你可以把这个文件当作模块导入其他程序中,并用一行代码调用它。请记住,模块是一个可以在其他Python程序中使用的Python程序。你可能已经意识到模块是代码的一种抽象(Abstraction)表示方法。抽象意味着你不必关注代码的所有细节。抽象的原则就是封装(Encapsulation),它会隐藏行为的细节。将加载文件的代码封装到一个模块中,这样在另一个程序中就不必关注它的实现细节。
清单2-1将一个字典文件加载至列表中的模块代码
load_dictionary.py\n&34;&34;&34;\n?importsys\n\n?defload(file):\n&34;&34;&34;\ntry:\nwithopen(file)asin_file:\n?loaded_txt=in_file.read().strip().split(&39;)\n?loaded_txt=[x.lower()forxinloaded_txt]\nreturnloaded_txt\nexceptIOErrorase:\n?print(&34;.format(e,file),\nfile=sys.stderr)\nsys.exit(1)
在文档字符串之后,为了让错误处理代码起作用,我们通过导入sys模块来调用一些系统函数?。接下来的代码段定义了一个load()函数,该函数基于前面讨论过的文件加载方法实现?,它以要加载的文件名为参数。
若打开文件时没有引发异常,则删除文本文件中的空格,并将各数据项单独分成一行保存至列表变量中?。在函数返回列表之前,让每个单词都成为列表中的一个单独项。由于Python会区分字符的大小写,因此使用列表推导(ListComprehension)方法将所有单词统一转换为小写?。列表推导是一种将列表或其他可迭代对象转换为另一个列表的快捷方法。在本例中,列表推导起到for循环的作用。
如果遇到I/O错误,程序会显示标准错误消息,并根据错误消息的描述参数e显示该事件产生的原因,同时向用户发出程序即将结束的提示?。然后,使用sys.exit(1)命令终止程序。
这段示例代码是为了说明这些步骤的功能。一般来说,你不会直接调用sys模块的exit()函数,在程序结束之前,你可能还希望它做一些其他的事情,例如向日志文件中写入数据。为了使代码简洁和易于控制,在后面的章节中会把try-except代码块和sys.exit()语句都写到main()函数中。
2.2项目2:寻找回文单词
首先,你将在字典文件中寻找回文单词。然后,你将学习寻找更为困难的回文短语的方法。
目标
使用Python在英文字典文件中搜索回文。
2.2.1策略和伪代码
在开始编写代码之前,先想一想你要做什么。识别回文是一件很容易的事情,即将一个单词简单地与它自身的反向切片进行比较。下面是一个生成单词正向切片和反向切片的示例:
>>>word=&39;\n>>>word[:]\n&39;\n>>>word[::-1]\n&39;
当对字符串(任何可分割类型)做切片操作时,若不提供切片的区间和步长,则默认的起始和终止位置分别是字符串的开头和结尾,步长等于1。
图2-1所示为反向切片的完整过程。本例指定的起始位置为2,步长为?1。由于没有提供结尾索引(在冒号之间没有指定索引值或设置空格),因此在执行切片操作时,将从后向前逐个(步长为?1)遍历字符串中的单词,直到没有字符剩下为止。
图2-1单词“NURSES”的反向切片示例
反向切片与正向切片的行为并不完全相同,这种不同主要表现在起始位置值的设置以及对端点的处理。这种不同可能会混淆正反向切片,为了避免这一问题,我们将单词的反向切片简单地设置为[::-1]。
与加载字典文件相比,在字典中查找回文单词所需的代码更少。下面是查找回文单词的伪代码:
以列表的形式加载字典文件中的单词\n创建一个空列表,保存查找到的回文单词\n循环遍历列表中的每个单词:\n如果单词的正向切片与反向切片相同:\n将该单词添加到回文单词列表中\n输出回文单词列表
2.2.2寻找回文单词的代码
清单2-2是程序palindromes.py的源代码,该程序会判断从字典文件中读取的哪些单词是回文,并将这些回文单词保存到一个列表中,最后输出列表中的各个回文单词项。从本书的配套资源中可以下载到这段代码。除此以外,还需要用到程序load_dictionary.py和一个字典文件。记住,将这些文件保存在同一目录下。
清单2-2从加载的字典文件中寻找回文单词
palindromes.py\n&34;&34;&34;\n?importload_dictionary\n?word_list=load_dictionary.load(&39;)\n?pali_list=[]\n\n?forwordinword_list:\niflen(word)>1andword==word[::-1]:\npali_list.append(word)\n\nprint(&34;.format(len(pali_list)))\n?print(*pali_list,sep=&39;)
首先,将程序load_dictionary.py当作一个模块导入本程序?。需要注意的是,在导入模块时不必输入文件的扩展名.py。此外,这个模块应该与本程序位于同一目录下。这样就不必指定该模块的路径名。由于导入的这个模块(load_dictionary)已经包含导入语句importsys,因此我们不需要在本程序里重复导入它。
为了用字典中的单词填充定义的单词列表,使用点符号调用load_dictionary模块中的load()函数?。将字典文件的名称当作该函数的参数。同样地,若字典文件与Python程序位于同一目录下,则不需要指定该文件所在的路径。本程序使用的字典文件可能与你使用的字典文件有所不同。
接下来,创建一个保存回文的空列表?。然后循环遍历word_list列表中的每个单词?,判断单词的正向切片与反向切片是否相同。如果这个单词本身与它的切片相同,那么将该单词添加到列表pali_list中。需要注意的是,含有一个字母以上的单词(len(word)>1)才满足回文的严格定义。
最后,单独输出列表中的各个回文单词,即输出的单词之间没有分隔符(引号或逗号)?。通过循环遍历列表中每个单词的方式也可以实现这样的功能,但是这里采用一种更加高效便捷的做法,即使用分拆操作符(SplatOperator)——在对象前加上符号*。在本程序中,分拆操作符以列表为输入,将列表中的每个元素分拆成函数的位置参数。函数print()的最后一个参数的作用是:设置数据之间的分隔符,默认的分隔符是空格(sep=&39;)。然而,本程序想把每个回文单词都单独输出在一行上(sep=&39;)。
在英文中,回文单词相当少见。对于一个含有60000个单词的字典文件,若足够幸运,你可能会找到大约60个或者说约0.1%的回文单词。尽管回文单词不太常见,但是利用Python程序很容易找到它们。现在,让我们来看看更有趣、更复杂的回文短语。
2.3项目3:寻找回文短语
与寻找回文单词相比,寻找回文短语(Palingram)需要考虑更多事情。在本节中,我们将编写一个查找回文短语的程序。
目标
使用Python在英文字典中搜索两个单词构成的回文现象,并使用cProfile工具来分析和优化这段搜索回文短语的代码。
2.3.1策略和伪代码
“nursesrun”和“stirgrits”就是两个回文短语的例子,如图2-2所示。与回文单词类似,从回文短语中间的字母开始,它从前读和从后读都是一样的字母序列。我喜欢把这样的“中间字母或字母组”当作核心词(CoreWord)。对单词“nurses”来说,它由回文序列(PalindromicSequence)和倒序词序列(ReversedWord)派生而来。
图2-2剖析回文短语
本项目对应的程序会检查回文短语的核心词。根据图2-2的描述,可对核心词的特点做出以下推论。
1.核心词的字母数量既可以是奇数,也可以是偶数。
2.从核心词的开头部分起,当反向读取字母序列时,这些连续的字母会拼凑成一个单词(FirstPart)。
3.这个连续的部分由核心词的部分字母或者全部字母组成。
4.核心词剩余部分的连续字母构成回文序列(SecondPart)。
5.回文序列可以由核心词的部分字母或全部字母组成。
6.回文序列不一定是一个真正的单词(除非它由该单词的所有字母组成)。
7.这两个部分不能重叠或共享字母。
8.回文序列本身是可逆的。
注意
如果整个核心词都由倒序词组成,而核心词又不是回文单词,那么这样的单词被称为回字(Semordnilap)。回字类似于回文单词,它们间关键的区别是:回文单词倒读时会拼写成相同的单词,而回字倒读时会拼写成一个不同的单词。例如,单词bats与单词stab互为回字,单词wolf与单词flow互为回字。
图2-3所示为由6个字母组成的任意单词。“X”代表单词的一部分,当倒着读时,它可能会组成一个真正的单词(例如单词“nurses”中的“run”)。“O”表示可能的回文序列(例如单词“nurses”中的“ses”)。图2-3中左侧的单词会组成一个类似于图2-2中nurses的单词,它们的开头都由一个倒序词组成。图2-3中右侧的单词会组成一个类似于图2-2中grits的单词,倒序词位于单词的末尾部分。需要注意的是,单词的组合数等于每一列中单词的字母总数加1。还需要注意的是,顶部和底部的行代表两种相同的情况。
图2-3在含有6个字母的核心单词中,倒序部分(X)和回文序列(O)的可能位置
每一列的最顶行代表回字,最底行代表回文。回字和回文都属于倒序词,只是它们属于不同的倒序词类型而已。因此,将回字和回文视为同一种东西,并且在循环中用一行代码就可判断出它们。
若要查看实际的关系图,请参考图2-4所示。从图中可以看出,在回文短语“devilslived”和“retroporter”中,单词“devils”和单词“porter”都是核心词。这两个短语在回文序列和倒序词方面互为镜像。以回字evil和回文kayak为例,比较这两种情况。
图2-4单词、回字和回文中的倒序部分(X)和回文序列(O)
回文既是倒序词又是回文序列。由于回文与回字具有相同的X模式,因此可以使用处理回字的代码来处理回文。
从策略上来讲,你需要循环遍历字典中的每个单词,判断其是否属于图2-3中的某个组合。假设字典文件中有60000个单词,则程序大约需要做500000次判断。
为了理解这个循环,请查看图2-5中回文“stackcats”的核心单词。你的程序需要循环遍历单词中的每个字母,遍历过程从结尾的字母开始;下次迭代时增加一个字母,即从次尾字母开始,依次类推。为了找到像“stackcats”这样的回文短语,还要判断核心词(stack)的末尾是否存在回文序列,以及它的开头是否存在一个倒序单词。需要注意的是,图2-5所示的第一个循环判断就会成功,因为在回文短语中,单独的字母(k)也能组成回文。
图2-5当循环遍历核心词时,寻找回文序列和倒序词
但是,这样做还不够。如果想判断它是否存在图2-3中的“镜像”现象,你必须倒着执行遍历过程,即从单词的开头查找回文序列,从单词的结尾查找倒序词。这种方法可以让你找到像“stirgrits”这样的回文短语。
下面是查找回文短语的伪代码:
以列表的形式加载字典文件中的内容\n创建一个保存回文短语的空列表\n遍历列表中的每个单词:\n获取单词的长度\n如果单词长度大于1:\n遍历单词中的每个字母:\n如果该单词前面的字母组成倒序词,并且该单词剩余的字母构成回文序列:\n将单词及倒序词添加至回文短语列表中\n如果该单词末尾的字母组成倒序词,并且该单词前面的字母组成回文序列:\n将单词及倒序词添加至回文短语列表中\n按照字母表顺序对列表中的回文短语排序\n输出回文短语列表中的回文单词对
2.3.2寻找回文短语的代码
清单2-3是程序palingrams.py的代码实现。该程序先循环遍历单词列表,确定哪些单词对构成回文短语,再将这些回文短语对保存到列表中,并单独输出回文列表中的各个数据项。从本书的配套资源中可以获得该程序。当开始本项目时,建议以2of4brif.txt为项目的字典文件,这样程序的运行结果会与本书所给的结果一致。记住,将字典文件、程序load_dictionary.py以及程序palingrams.py放到同一目录下。
清单2-3在已加载的字典中查找和输出回文短语
palingrams.py\n&34;&34;&34;\nimportload_dictionary\n\nword_list=load_dictionary.load(&39;)\n\n34;&34;寻找字典中的回文短语。&34;&根据短语的第一个单词,对回文短语进行排序\npalingrams_sorted=sorted(palingrams)\n\n34;\\nNumberofpalingrams={}\\n&34;{}{}&39;&39;palingrams.find_palingrams()&39;append&39;list&34;Runtimeforthisprogramwas{}seconds.&34;&34;寻找字典中的回文短语。&34;”\npali_list=[]\n?words=set(word_list)\n?forwordinwords:\nend=len(word)\nrev_word=word[::-1]\nifend>1:\nforiinrange(end):\n?ifword[i:]==rev_word[:end-i]andrev_word[end-i:]inwords:\npali_list.append((word,rev_word[end-i:]))\n?ifword[:i]==rev_word[end-i:]andrev_word[:end-i]inwords:\npali_list.append((rev_word[:end-i],word))\nreturnpali_list
与原来的代码相比,优化后的代码只有4行发生改变。定义一个新的变量words,用它来保存word_list列表对应的集合?。然后,遍历整个集合?。在这个集合中查找单词的切片并判断它是否属于该集合??,而以前该操作作用的对象是列表。
下面是程序palingrams_optimization.py中新的find_palingrams()函数运行时所耗费的时间:
Runtimeforthisprogramwas0.4858267307281494seconds.
哇!程序的运行时间由3分钟减少为不足一秒!这就是优化!这两个程序的不同之处在于采用的数据结构。验证单词是否属于列表是一个非常耗费时间的操作。
为什么刚开始时我向你介绍“错误”的方法呢?因为实际情况就是这样的。你必须先让代码正常运行,然后考虑代码的优化。这是一个有经验的程序员从一开始就会考虑到优化的简单例子,但是它蕴含着优化的整体思想:尽全力先让程序运行起来,然后让程序变得更好。
本文摘自:《Python编程实战》
你可以把本书当作学习Python的辅助类图书。本书是一本完全面向初学者的入门图书。在本书中,你将使用基于项目的方法进行自我训练。本书不会浪费你的金钱和书架空间,也不是对你已学过的知识概念的重新整理。不过,请别担心!本书不会让你独自去完成这些项目,书中所有的代码均有注释和解释。
本书的这些项目适用于希望通过编程进行实验仿真、理论验证、自然现象模拟和获取快乐的人。其中包括那些将编程作为工作的一部分但并不是程序员的人(如科学家和工程师),还包括那些“非专业人士”——编程的业余爱好者和把编程当作娱乐消遣的人。如果你想弄明白本书提到的项目,但又发现自己从头开始做这些复杂的项目会非常艰巨或耗费大量时间,那么本书就很适合你。
本书基于Python语言,通过项目展示Python的奇妙应用,适合Python初学者学习。在本书中,你将使用Python编程语言模拟探索火星、木星以及银河系最遥远的地方,体验诗人的意境,了解高级的金融知识等。你还会学到各种各样的技术,如马尔可夫链分析技术、蒙特卡罗模拟、图像叠加技术、基因遗传算法等。与此同时,你还会学习一些模块的使用方法,例如pygame、Pylint、pydocstyle、Tkinter、python-docx、Matplotlib和pillow等。
好了,文章到这里就结束啦,如果本次分享的如何获取漫画资源源码分享网站和漫画源码app问题对您有所帮助,还望关注下本站哦!
