参考博客:https://www.cnblogs.com/TheFutureIsNow/p/11963233.html

More Basic Tactics (Tactics)
• The apply Tactic
• The apply with Tactic
• The injection and discriminate Tactics
• Using Tactics on Hypotheses
• Varying the Induction Hypothesis
• Unfolding Definitions
• Using destruct on Compound Expressions

介绍几种更为复杂的证明策略:

[apply]策略

• the goal to be proved is exactly the same as some hypothesis in the context or some previously proved lemma. (目标和 假设相同)
• 要使用[apply]策略,所应用的事实(结论)必须与目标完全匹配—例如,如果等式的左右两边交换,apply将不起作用,这个时候就需要使用关键字[symmetry]将等式的两边进行交换

在进行证明的时候经常遇到这样的情况,即要证明的目标与上下文中的某个假设或某个先前已证明的引理完全相同。
有时候可以使用[rewrite]然后在使用[reflexivity]来完成证明,如:

但也可以使用[apply]策略一步完成证明:

hypothesis n=m
goal n=m 二者相同

[apply]策略也适用于条件假设和引理:
apply用于化解 蕴含
举例

eq n = m -> [n; o] = [m; p]
goal [n; o] = [m; p]

apply eq后

goal n=m

连环蕴含


通常,当我们使用**[apply H]时,而语句H是以关键字forall开始的,也就是说语句H绑定了一些通用的变量。当Coq根据H的结论匹配当前目标时,它将尝试为这些变量找到合适的值。例如,在上面的例子中使用语句[apply eq2]时,eq2中的通用变量q用n实例化,r用m实例化**。

需要注意的一点是,要使用[apply]策略,所应用的事实(结论)必须与目标完全匹配—例如,如果等式的左右两边交换,apply将不起作用,这个时候就需要使用关键字**[symmetry]将等式的两边进行交换:

[apply with]策略

[apply with]和[apply]其实没有太大区别,只不过[apply with]允许指定用上下文中的变量代替引用的假设或者结论中的绑定变量。
先看一个例子:
证明方法1 - rewrite

证明方法2 -apply with

直接使用apply 无法寻找到变量

使用apply with

apply可以告诉(通过匹配目标和结论),它应该用[nat]来实例化X,用[a,b]来实例化n,用[e,f]来实例化o。然而,这个匹配过程并不能确定m的实例化

我们必须通过在apply的调用中加入 "with (m:=[c,d]) "来明确地提供一个实例。apply with可以指定上下文中的变量作为重写的参数。
实际上,with子句中的名称m不是必需的,因为Coq通常足够聪明,能够弄清楚我们正在实例化哪个变量。我们可以简单地写成apply trans_eq with [c;d]。

证明方法3 -transitivity

[injection]和[discriminate]策略

回顾之前定义自然数的语句:

从定义的语句中很明显能够看出,每个自然数都只能是两种情况中的一种:要么是是由构造器O构成的,要么是由构造器S中构成的。这也是基础证明策略[destruct]和[induction]的基本原理。
然而还能够从自然数的定义语句中看出两外两点:这两条规则可以适用于任何一个递归定义的变量类型。

这个定理也可以使用[injection]策略进行证明:

injection
injection H as 新的H们(由H推导出的内容)

通过[injection H]语句,Coq会生成它可以依据构造函数的单射性推导出的所有方程。每一个这样的方程都是作为目标的前提加入的,而在这个例子中,添加了前提n=m。而这些前提也会成为后续证明的子目标。
此外,还可以使用关键字as引入一个变量来绑定这些前提,如:


不相交原则是指两个变量以不同的构造函数(如[O]和[S],或[true]和[false])永远不可能相等。这意味着,任何时候我们发现上下文中某个假设断言两个不同构造器的变量相等,那么就可以得到任何想要的结论,因为假设是不成立的。
即 由 非、不可能成立的东西 推出 all
[discriminate]策略具体化了这个原则,通常这个策略被用在某个断言两个不同构造器构造的变量相等的假设上,然后使用这个策略快速完成当前的目标。例如:

可以将[discriminate]策略理解为:如果证明过程中某个荒谬的假设成立,那么推出的任何结论也是成立的,如:

此时蕴含语句,需要intro 引入H 和goal

H中存在E,H 其中H未谬论,所以可推导出任何结论

[unfold]

有时在证明过程中需要手动展开一个已经被一个[Definition]所定义好的函数名称,以便更好操纵等式的右边。
例如,定义一个平方函数:

Definition square n := n * n.

然后基于这个定义进行以下证明:

Theorem square_mult : forall n m, square (n * m) = square n * square m.
Proof.
intros n m. (*Did nothing*)unfold square.
rewrite mult_assoc.
assert (H : n * m * n = n * n * m). {rewrite mult_comm. apply mult_assoc. }rewrite H. rewrite mult_assoc. reflexivity.
Qed.

【coq】函数语言设计 笔记 05 -tactics相关推荐

  1. 【历史上的今天】6 月 5 日:洛夫莱斯和巴贝奇相遇;公钥密码学先驱诞生;函数语言设计先驱出生

    整理 | 王启隆 透过「历史上的今天」,从过去看未来,从现在亦可以改变未来. 今天是 2022 年 6 月 5 日,世界环境日.1972 年 6 月 5 日至 16 日,联合国人类环境会议在斯德哥尔摩 ...

  2. [C++程序语言设计笔记一]面向对象编程抽象,继承,重写基本介绍

    今天是个不错的日子,不仅有人收了我做徒弟从此传授我有关C++的一些知识,由于前一段时间喜欢上了外挂的研究也用到了一些MFC的知识及一些Windows APIs编程,但是对C++还是没有从根本上认识.我 ...

  3. C语言学习笔记10-指针(动态内存分配malloc/calloc、realloc、释放free,可变数组实现;Tips:返回指针的函数使用本地变量有风险!;最后:函数指针)

    C语言:指针 1. 指针:保存地址的变量 *p (pointer) ,这种变量的值是内存的地址.   取地址符& 只用于获取变量(有地址的东西)的地址:scanf函数-取地址符   地址的大小 ...

  4. r语言c函数怎么用,R语言学习笔记——C#中如何使用R语言setwd()函数

    在R语言编译器中,设置当前工作文件夹可以用setwd()函数. > setwd("e://桌面//") > setwd("e:\桌面\") > ...

  5. c 语言filter过滤方法,R语言日常笔记(1)filter函数

    R语言日常笔记(1)filter函数 在处理数据时,过滤数据是最基本的操作之一. 如果想删除一部分无效或者根本不感兴趣的数据. dplyr有filter()函数来做这样的过滤. 使用dplyr,可以帮 ...

  6. R语言与函数估计学习笔记(函数模型的参数估计)

    R语言与函数估计学习笔记 毫无疑问,函数估计是一个比参数估计要复杂得多的问题,当然也是一个有趣的多的问题.这个问题在模型未知的实验设计的建模中十分的常见,也是我正在学习的内容的一部分. 关于函数估计我 ...

  7. C 语言的可变参数表函数的设计

    首先在介绍可变参数表函数的设计之前,我们先来介绍一下最经典的可变参数表printf函数的实现原理. 一.printf函数的实现原理 在C/C++中,对函数参数的扫描是从后向前的.C/C++的函数参数是 ...

  8. c语言中void arrout,c语言学习笔记(数组、函数

    <c语言学习笔记(数组.函数>由会员分享,可在线阅读,更多相关<c语言学习笔记(数组.函数(53页珍藏版)>请在人人文库网上搜索. 1.数组2010-3-29 22:40一维数 ...

  9. c语言学习笔记【结构体02】结构体指针变量与结构体变量的函数参数,C语言学习笔记结构体02结构体指针变量与结构体变量的函数参数.docx...

    C 语言学习笔记[结构体02]结构体指针变量与结构体变量 的函数参数 C 语言学习笔记之结构体指针变量一提指针,那可 是 C 语言的核心了,有多少学子曾拜倒在指针的脚下.单纯的说指针,其实并不难,但是 ...

  10. C语言程序设计笔记(浙大翁恺版) 第七章:函数

    按照中国大学MOOC上浙江大学翁恺老师主讲的版本所作,B站上也有资源.原课程链接如下: https://www.icourse163.org/course/ZJU-9001 由于是大三抽空回头整理的, ...

最新文章

  1. 【融云分析】如何实现分布式场景下唯一 ID 生成?
  2. 哪些情况是友情链接作弊?总结了11种方法!
  3. 如何使用PHP发送电子邮件?
  4. JAVA8给我带了什么——并流行和接口新功能
  5. 6月全球垃圾邮件上升6.9% 以色列高居榜首
  6. Nginx爆出新漏洞,谨防“拖库”风险
  7. 速腾(Robosense) M1激光雷达ip配置
  8. 转录组-蛋白组-代谢组关联分析
  9. 按下删除键出现 ^H 乱码现象总结
  10. c语言-计算摄氏温度
  11. blowfish java_Java与C++通过CBC、blowfish互相加解密
  12. Maven阿里云镜像以及仓库地址修改
  13. 实体门店为什么要做共享股东模式
  14. ZZULIOJ1097: 计算平均成绩(函数专题)
  15. Unity 创建Sprite导致的内存溢出奔溃问题
  16. Android 个人中心界面实现
  17. Hypervisor---虚拟化技术简易说明
  18. 数据库的主键约束和自增长
  19. C#毕业设计——基于C#+asp.net+sqlserver药店进销存管理系统设计与实现(毕业论文+程序源码)——进销存管理系统
  20. Your branch is up to date with 'origin/master'.但是本地代码却不是最新的

热门文章

  1. 推荐 :数据科学研究的现状与趋势
  2. 2018-8-10-win10-uwp-使用资源在后台创建控件
  3. Python教程:输入一系列整数输出最大值
  4. 在虚拟机上使用macvlan命令建虚拟网卡
  5. Cabbage教学(2)——类型转换与字符串操作
  6. fflush(stdout)
  7. 木门锁孔合页综合加工机器
  8. 【文献管理】Zotero基础操作
  9. 先决条件检查失败错误
  10. 西安电子科技大学-概率论与数理统计大作业-概率论与数理统计在日常生活和社会经济中的应用