我需要类型为num的二进制和十六进制语法翻译

时间:2014-03-26 06:21:55

标签: isabelle

我先问我的问题。

问题:我需要num数据类型的二进制和十六进制语法。我可以轻松适应某些地方吗?有人能为我提供吗?或者,它已经存在了吗?

数字类型类允许使用二进制和十六进制表示法,例如0b01010xAA。但是,num未实例化为numeral,我只看到直接使用的构造函数,例如使用此源:

primrec sqr :: "num => num" where
  "sqr One = One" |
  "sqr (Bit0 n) = Bit0 (Bit0 (sqr n))" |
  "sqr (Bit1 n) = Bit1 (Bit0 (sqr n + n))"

下面,我提供了一个完整的理论,其中我已经定义了符号,允许我使用num的二进制和十六进制表示法,但它不是标准符号。我所接受的符号是可以接受的,但看起来它最终可能会引起一些冲突。

我最初构建表格以了解如何使用OneBit0Bit1来创建二进制数。起初它很棘手,因为位的顺序与正常情况相反,还有一些其他的怪癖,但我终于明白了。对于任何有兴趣的人,有一些关于num以及numeral wiki page的好消息:

  • 最重要的数字位于右侧,而不是左侧。
  • num类型没有零,所以最右边的数字总是1,但是当你在左边添加足够的数字时,最右边的数字的值增加2的幂。
  • 在左侧添加零会使数字更大。

包含的理论太过涉及将其转换为ASCII。有些人可能有兴趣在PIDE中加载它来查看它。我在底部显示了一个用法,用于定义函数num_left_shift

我只是在寻找具有2个字符前缀的语法,如0u1010101,以及像0m555这样的十六进制语法。语法的翻译将从num构造函数构建一个数字。

我无法让translations为我工作。我也看到在Num.thy中使用parse_translation,但我不知道如何使用它。

更新:140326

我更新这个来回答Brian Huffman的问题。我在这里这样做,因为它需要更多的字符而不是评论允许。 Brian的问题是:

  

您是否需要直接使用type num?为什么不定义一种单独的自然类型> 0,并使其成为类数字的实例?

简短的回答是我不需要num,因为它没有零,我需要它,因为这是我知道在位级别使用二进制和十六进制fun的唯一方法。特别是,我在谈论与fun的模式匹配,二进制和十六进制模式。

从这里,我谈到num如何成为我的大计划的一部分,以及为什么我认为我需要它来进行二进制位移。

数字用于抽象,nat用于Suc,num用于One,Bit0和Bit1

这与我最终尝试在代数类型类中做很多工作的计划有关。

采用类型类linordered_idom。如何充分利用HOL的强大功能?我没有,因为我没有构造函数可以使用。

我花了几天的时间尝试使用datatypetypedef将构造函数放在UNIV::'a::linordered_idom set上,尽管它也有零个拥有自己的构造函数。

它有点奏效,但它是一堆混乱,而不是一个完全好的解决方案。

这导致我的想法是使用nat作为一种方法来使用numeral(num_of_nat)来支持所有数字。

作为其中的一部分,我定义了一个计算十进制数字位数的函数:

fun dec_digits :: "nat => nat" where
  "dec_digits n = (if (n div 10 = 0) then 1 else 1 + dec_digits(n div 10))"

我假设对二进制数的位移操作比div快,所以我开始寻求二进制位移函数来使用二进制和十六进制数,这导致num

这与上面的章节标题有关。使用nat,我通过添加一个构造函数来构建数字。但是如何使用nat进行二进制位移?

我对numeralnum有很多不了解,但我的结论是,作为处理数字的完整解决方案,我需要使用{{1}的所有三个},numeralnum

二进制和十六进制除法的左移位

函数nat是我初步努力的一部分,是为了解决未来的一些基本思想,与数字系统及其与代数类型类的关系。

num_left_shift类型是HOL的基础,而nat对它起着很大的作用。 fun类型类为我提供了一组抽象的数字常量,通过代数二进制操作,您可以使用它来处理大量的低级魔法。

但是如何根据结构操纵数字呢?我知道HOL中有很多数学运算,例如numeraldiv,但如何在不使用mod的情况下进行二进制位移?

我现在所知道的是如何使用num为二进制和十六进制执行此操作。如果有一个高水平的方法,我会很高兴了解它。

我仍然有一个问题是,“如何在不使用num的情况下根据小数位操作HOL中的数字?

div

1 个答案:

答案 0 :(得分:0)

现在,我对此表示满意。并不是说我仍然不喜欢开发人员的某种答案,但我不想在事情发生变化时浪费时间。

我在此处显示,我已经从想要直接使用num变为想要使用(num => num) list,这已经改变了对语法实现方式的需求。

num有两个限制,它没有零,而且通过模式匹配,我只能在右侧有一个变量,而我所有的位模式都必须是构造函数。< / p>

结果是如果我想匹配n位,我必须有(n+1) - 1个案例,如果我在这里的某些细节上错了,那么现在就不重要了。

在这里,我展示了需要15个案例来匹配3位:

notation Num.One  (":1:")
notation Num.Bit0 ("0:_" [1000] 1000)
notation Num.Bit1 ("1:_" [1000] 1000)

fun xp_3_bit_match :: "num => num" where
  "xp_3_bit_match :1: = :1:"
 |"xp_3_bit_match (0::1:) = :1:"
 |"xp_3_bit_match (1::1:) = :1:"
 |"xp_3_bit_match (0:0::1:) = :1:"
 |"xp_3_bit_match (1:0::1:) = :1:"
 |"xp_3_bit_match (0:1::1:) = :1:"
 |"xp_3_bit_match (1:1::1:) = :1:"
 |"xp_3_bit_match (0:0:0:n) = :1:"
 |"xp_3_bit_match (1:0:0:n) = :1:"
 |"xp_3_bit_match (0:1:0:n) = :1:"
 |"xp_3_bit_match (1:1:0:n) = :1:"
 |"xp_3_bit_match (0:0:1:n) = :1:"
 |"xp_3_bit_match (1:0:1:n) = :1:"
 |"xp_3_bit_match (0:1:1:n) = :1:"
 |"xp_3_bit_match (1:1:1:n) = :1:"

接下来,我在类型(num => num) list上进行模式匹配,并将15个案例减少到4.如果我将[]映射到numnat的第一个案例会给我一个零notation (input) Num.Bit0 ("\<zero>") notation (input) Num.Bit1 ("\<one>") fun num_num_3_match :: "(num => num) list => num" where "num_num_3_match [] = Num.One" |"num_num_3_match [_] = Num.One" |"num_num_3_match [b1,_] = b1(Num.One)" |"num_num_3_match [b1,b2,_] = b2(b1(Num.One))" |"num_num_3_match (b1 # b2 # b3 # bs) = b3(b2(b1(num_num_3_match bs)))" term "num_num_3_match [\<one>,\<one>,\<zero>,\<zero>,\<one>,\<one>]" value "num_num_3_match [\<one>,\<one>,\<zero>,\<zero>,\<one>,\<one>]" ,反之亦然。

fun numL :: "(num => num) list => nat" where        
  "numL []  = 0"
 |"numL [_] = 1"
 |"numL [Num.Bit0,_] = 1" 

 (*exception Option raised (line 81 of "General/basics.ML")*)        

fun numL :: "(nat => nat) list => nat" where
  "numL []  = 0"
 |"numL [Suc,_] = 1"    

但是,对于构造函数而不是变量,我会遇到异常错误,但这可能是因为我使用的是构造函数。

{{1}}