关于randomize()这个函数,发现我之前对它的理解有误。对pre_randomize()和post_randomize()的理解更是糟糕,下面我们就来整理一下他们之间的关系。
在绿皮书的6.3.2中,对randomize()函数的描述如下:randomize()函数为类里面所有的rand和randc类型的随机变量赋一个随机值,并保证不违背所有有效约束。
在绿皮书的6.9中,对pre_randomize()和post_randomize()的描述如下:有时需要在调用randomize()之前或者之后立即执行一些操作,SystemVerilog可以使用两个特殊的void类型的pre_randomize()和post_randomize()函数来完成这项功能。
也就是说在pre_randomize与post_randomize是在randomize的前后,并不参与solver的求解,而是在solver求解完以后对其进行随机数的调整。
实际上,randomize()函数是自己去调用这两个函数!!!!
案例分析:
- randomize()会自己调用pre_randomize()和post_randomize()这两个函数。
- 如果没有定义pre_randomize()和post_randomize()这两个函数,那么就可以认为这两个函数是什么也不做的。
- 可以根据自身需要重写pre_randomize()和post_randomize()这两个函数。
- 这儿可能会想到,对这些在pre_randomize()中设置的变量,也可以在别的地方设置,比如在自己另写的function_x中对该变量进行设置。但是这样每次进行randomize()之前都要手动调用一次function_x,这样是很不方便的,而且也不容易遗忘或出错。
补充
- slover...before 不能用randc的类型
- randomize(src) 里面有src和drc两个变量的结果。()里面是谁,就仅仅对谁进行进行随机,剩下的尽采用默认值(但是也会进行约束求解),也就是randmize(src) + drc==default ->满足所有的约束。
- 随机只能产生0/1,所以可以在post_randomize()里面设置对随后后的值设置x态等。
- pre/post_randmize()其实并没有做任何随机的操作,只不过是在随机的前后做一些function的操作而已,对随机的结果进行调整。可以改变随机的值。
上述例子进一步说明了,pre/post_randomize()并没有参数随机,就是在随机前和随机后,做了一些function的操作。