首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >创建逻辑门模拟器

创建逻辑门模拟器
EN

Stack Overflow用户
提问于 2009-06-10 12:11:22
回答 7查看 7.3K关注 0票数 9

我需要创建一个应用程序来创建逻辑电路并查看结果。它主要用于A-Level (英国,通常为16-18岁)计算课程。

我从来没有做过这样的应用,所以我不确定存储电路和评估结果的最佳设计(以可恢复的速度,比如1.6 the单核计算机上的100 am )。

与其从基本的门(and,or,nand等)构建电路,我想让这些门被用来制造“芯片”,然后可以在其他电路中使用(例如,你可能想要制造一个8位寄存器芯片,或一个16位加法器)。

问题是,随着这样的电路,门的数量会大量增加,这样如果在每个单独的门上进行模拟,它将有1000个门要模拟,所以我需要简化这些可以放置在电路中的组件,以便可以快速地对它们进行模拟。

我考虑为每个组件生成一个真值表,然后模拟可以使用查找表来查找给定输入的输出。然而,问题出现在我身上,这些表的大小随着输入的增加而大量增加。如果一个芯片有32个输入,那么真值表需要2^32行。这在许多情况下使用了大量的内存,因此对于非平凡的组件是不实用的,它也不适用于可以存储其状态(例如寄存器)的芯片,因为它们不能被表示为简单的输入和输出表。

我知道我可以硬编码像寄存器芯片这样的东西,但是因为这是出于教育目的,所以我想要它,这样人们就可以制作自己的组件,以及查看和编辑标准实现。我考虑允许使用代码(例如dlls或脚本语言)创建和编辑这样的组件,这样加法器就可以表示为"output = inputA + inputB“,但是这假设学生已经用给定的语言做了足够的编程,能够理解和编写这样的插件来模拟他们电路的结果,这可能不是这样的……

有没有其他方法可以将布尔逻辑电路自动简化,以便模拟可以快速确定组件的输出?

至于存储组件,我正在考虑存储某种类型的树结构,这样一旦链接到其输入的所有组件都被评估,就会对每个组件进行评估。

例如:A。B+ C模拟器将首先评估AND门,然后使用and门和C的输出评估OR门。

然而,我突然想到,在输出链接回输入的情况下,会导致死锁,因为输入永远不会都是evaluated...How。我能克服这个问题吗,因为程序一次只能计算一个门?

EN

回答 7

Stack Overflow用户

发布于 2009-06-10 12:15:52

你有没有看过Richard Bowles's simulator

票数 5
EN

Stack Overflow用户

发布于 2009-06-10 12:24:48

你不是第一个想要构建自己的电路模拟器的人;-)。

我的建议是确定一个最小的原语集。当我开始我的工作时(我计划有一天会恢复……)我有两个原语:

  • 源:零输入,一个输出始终为1。
  • 晶体管:两个输入AB,一个输出为A and not B.

显然,我有点滥用了这个术语,更不用说忽略了电子产品的精妙之处。关于第二点,我建议像我一样抽象为带有1和0的线。我从这些图中画出了门和加法器的图表,从中获得了很多乐趣。当你可以将它们组装成电路,并在集合周围画一个框(包括输入和输出)时,你就可以开始建造更大的东西,比如乘法器。

如果您希望使用循环,则需要加入某种延迟--因此每个组件都需要存储其输出的状态。在每个周期中,您将根据上游组件的当前状态更新所有新状态。

编辑关于您对可伸缩性的担忧,如何默认使用第一原理方法来模拟每个组件的状态和上游邻居,但提供优化子电路的方法:

  • 如果您有一个子电路S,其输入A[m]的m<8(例如,给出最多256行),输出B[n]且没有环路,则为S生成真值表并使用它。这可以为已识别的子电路自动完成(如果该子电路出现多次,则可以重复使用)或通过选择进行重复使用。
  • 如果您有一个具有环路的子电路,则您仍然可以生成真值表。这里有一些定点查找的方法可以帮助你。
  • 如果你的子电路有延迟(并且它们对封闭电路很重要),真值表可以包含状态列。例如,如果子电路具有输入A、内部状态B和输出C,其中C <- A和B,B <- A,则真值表可以是:

A B|B C

0 0|0 0

0 1|0 0

1 0|1 0

1 1|1 1

  • 如果用户断言某个子电路实现了特定的已知模式,如"adder",请提供一个选项,以便使用硬编码实现来更新该子电路,而不是通过模拟其内部部分。
票数 4
EN

Stack Overflow用户

发布于 2010-01-27 00:21:45

当我做了一个电路仿真器(不幸的是,也是不完整的,也没有发布),下面是我处理循环的方式:

  • 每个电路元素存储它的布尔值
  • 当一个元素"E0“改变它的值时,它通知(通过观察者模式)所有依赖它的人
  • 每个观察元素评估它的新值,并同样执行

当E0发生变化时,会保留一个包含所有受影响元素的1级列表。如果一个元素已经出现在这个列表中,它就会在一个新的二级列表中被记住,但不会继续通知它的观察者。当E0开始的序列已经停止通知新元素时,处理下一个队列级别。即:第一个元素添加到level-2,然后下一个添加到level-2,依此类推,直到所有level-x完成,然后您移动到level-(x+1)

这绝不是完整的。如果你曾经有多个振荡器在无限循环,那么无论你把它们放在什么顺序,其中一个可能会阻止另一个。我的下一个目标是通过使用基于时钟的同步而不是级联组合来限制步长来缓解这个问题,但我在我的项目中从未走到这一步。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/975211

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档