PyQt5
55篇
PyQt5:开局只有5个农民,从荒岛到建立帝国!(QTimer与QThread的综合应用举例)2
导读:现在是挖矿时间!
LEARN MORE
正文
上期我们展示了使用QTimer和QThread相结合的小例子,本期我们把代码部分一起研究学习下!
1
设计思路
整个程序我觉得可以分为以下几个方面:
1、进度条演示挖矿进度
2、多线程调用挖矿,避免UI界面被卡死
3、矿石类的建立
矿石单独用一个类表示,便于代码编写。
2
部分核心代码介绍
矿石类
这个矿石类Ore包含了两个函数,一个是digging()表示判断的矿石是否为金矿,一个是begin_dig()表示挖矿这个具体操作:挖多长时间等等。
second、goldnum表示具体的挖矿时间和挖到的金矿数量;start记录下开始挖矿的时间。
要是本地目录下没有gold.gd这个文件,给它创建这个文件,并写入一个空字符串。
注意:是空字符串不是字符串为空!对比如下:
原因知道了吗?
这个函数就是筛选金矿的函数了。
我们知道ASCII码使用指定的7位或8位二进制数组合来表示128或256种可能的字符,这里我们用的是8位,表示256种可能字符。
首先我们建立一个0-255的列表,每个元素对应具体的ASCII。
我们挖矿,得到的矿石(每一个ASCII码)都是随机的,但是金矿相对于其他矿石来说,含量更低,被挖到的可能性更小。所以我们在进行列表元素随机选择的时候,增加了权重的内容,让金矿被选中的几率降低。别的矿石都是100,它只有5。除非挖矿的时间长,否则出现的几率小。
根据Python3.5的官方文档介绍,random模块中增加权重的选择有三种方式:
方式一:
这种方式中,为了给元素增加权重,按照元素的权重构造了一个新的列表,如上述代码中的population。
在population中我们可以看到Red、Blue、Yellow、Green按照权重的方式各自新增元素,这就造成了使用choice()函数,即使是等几率的,出现的结果也会不一样,多的元素当然被选中的机会多啊!
方式二:
就是我们下面的这种写法了。
使用itertools.accumulate对权重进行累加,如:
接着我们利用random.random()与最后一个cumdist相乘,random.random()的范围是浮点数0.0-1.0(不含)。
bisect.bisect(cumdist, x)返回的是在有序列表cumdist中要插入元素x,返回其需要插入的位置。这个位置在ore_list中的元素就是我们需要挖取矿石。
因为金矿的权重和其它矿石相比权重很低,在itertools.accumulate(weights)列表中,这个插入点的位置出现的情况就会比较少,间接造成金矿出现的几率少。
不明白的话,再看看下面这个例子。
我们可以明显的看到第1与第2的元素之间有1个整数的位置,其它位置元素的之间的可以插入的整数位置较多,所以造成了低权重的数据被选中的几率低啊。
方式三:
针对Python3.6及以上,这个最简单了,直接使用函数
3.6版本新增!从population集群中随机抽取K个元素(可重复)。weights是相对权重列表,cum_weights是累计权重,两个参数不能同时存在。
例如,相对权重[10,5,30,5]等于累积权重[10,15,45,50]。在内部,相对权重在进行选择之前会转换为累积权重,因此提供累积权重可以节省工作量。
如果相对权重、累积权重均没有,则以相等的概率进行选择。如果提供了权重序列,则它必须与总体序列的长度相同。
因为我用的版本是Python3.5的,所以只能选择方式二了。
我们将得到的ASCII码,注意chr()转换一下,写入gold.gd文件,追加方式。当然你也可以不写这个,这里只是为了有点挖矿的意思。
同时返回是否是金矿的信息,是返回1,否返回0。
这里较为简单,我们进入一个挖矿的循环当中,并且记录挖到金矿的数量self.goldnum。
要是挖矿的时间和之前传入的挖矿要求时间一致,退出循环,并且返回金矿的数量。
3
最后
好的,今天这期就这样结束吧。以上是我自己写得挖矿的模拟,未必最优,仅供参考。如果你喜欢本篇文章,请给我点赞
赞赏(推荐)
分享给你的好友们吧!
领取专属 10元无门槛券
私享最新 技术干货