assert_param 函数,断言

2024-04-30 21:08
文章标签 函数 断言 assert param

本文主要是介绍assert_param 函数,断言,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

        在STM32的固件库和提供的例程中,到处都可以见到assert_param()的使用。在固件库中,它的作用就是检测传递给函数的参数是否是有效的参数。       

        这是一种常见的软件技术,可以在调试阶段帮助程序员快速地排除那些明显的错误。它确实在程序的运行上牺牲了效率(但只是在调试阶段),但在项目的开发上却帮助你提高了效率。

        当你的项目开发成功,使用release模式编译之后,或在stm32f10x_conf.h文件中注释掉对USE_FULL_ASSERT的宏定义,所有的assert_param()检验都消失了,不会影响最终程序的运行效率。

        assert_param函数在stm32f0xx_conf.h 库函数中定义:

/* Exported types ------------------------------------------------------------*/
/* Exported constants --------------------------------------------------------*/
/* Uncomment the line below to expanse the "assert_param" macro in theStandard Peripheral Library drivers code */
/* #define USE_FULL_ASSERT    1 *//* Exported macro ------------------------------------------------------------*/
#ifdef  USE_FULL_ASSERT/*** @brief  The assert_param macro is used for function's parameters check.* @param  expr: If expr is false, it calls assert_failed function which reports*         the name of the source file and the source line number of the call*         that failed. If expr is true, it returns no value.* @retval None*/
#define assert_param(expr) ((expr) ? (void)0 : assert_failed((uint8_t *)__FILE__, __LINE__))
/* Exported functions ------------------------------------------------------- */
void assert_failed(uint8_t* file, uint32_t line);   // 声明该函数
#else
#define assert_param(expr) ((void)0)                // 把assert_param(expr)定义为空
#endif /* USE_FULL_ASSERT */

        如果定义USE_FULL_ASSERT,就把 assert_param(expr) 定义为:  ((expr) ?  (void)0 : assert_failed((uint8_t *)__FILE__, __LINE__))  并申明一下assert_failed这个函数。没定义USE_FULL_ASSERT时即把assert_param(expr)定义为。 __FILE__和__LINE__是IAR定义的宏,指的是当前的编译的文件名行数。     

         整个宏作用为: 如果expr为真,则什么也不返回,如果expr为假,则调用assert_failed()这个出错程序。

        (条件) ? (条件成立执行部分) :(条件不成立执行部分)

例如:  a=( x>y ? x:y );       // 当x>y为真时,a=x,当x>y为假(即y>x)时,a=y。

注意: assert_failed()函数一般在代码调试时使用,先将头文件stm32f0xx_conf.h里面的宏定义/* #define USE_FULL_ASSERT    1 */ 注释去掉,可以帮助开发者检查输入参数无效的错误,但由于assert_failed()函数会影响代码执行效率,在程序release时,需要屏蔽掉,将宏定义USE_FULL_ASSERT注释即可。

举例说明:

  assert_param(IS_USART_ALL_PERIPH(USARTx));  

     这句代码用于检查参数USARTx是否有效,其中IS_USART_ALL_PERIPH(USARTx)是一个宏定义,如下:

#define IS_USART_ALL_PERIPH(PERIPH) (((PERIPH) == USART1) || \((PERIPH) == USART2) || \((PERIPH) == USART3) || \((PERIPH) == UART4) || \((PERIPH) == UART5))

        宏定义的功能是参数USARTx是USART1~USART8其中的一个,表示参数USARTx有效,不返回,否则返回assert_failed函数定义显示的内容。

       assert_failed函数可以从官方文件的模板中main.c中可以找到

#ifdef  USE_FULL_ASSERT/*** @brief  Reports the name of the source file and the source line number*         where the assert_param error has occurred.* @param  file: pointer to the source file name* @param  line: assert_param error line source number* @retval None*/
void assert_failed(uint8_t* file, uint32_t line)
{/* User can add his own implementation to report the file name and line number,ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) *//* Infinite loop */while (1){}
}

        里面英文注释也说明了怎么应用,通过输入参数来确定位置,最简单的方法就是串口打印了,这个函数的主要思想是在输入参数有问题的时候,但是有编译不出来,它可以帮你检查参数的有效性。 结果是输出到串口,用串口调试助手可以看到输出结果。注意,编译器Build Output栏是不会报错的。

 

 

这篇关于assert_param 函数,断言的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/949918

相关文章

postgresql使用UUID函数的方法

《postgresql使用UUID函数的方法》本文给大家介绍postgresql使用UUID函数的方法,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录PostgreSQL有两种生成uuid的方法。可以先通过sql查看是否已安装扩展函数,和可以安装的扩展函数

MySQL字符串常用函数详解

《MySQL字符串常用函数详解》本文给大家介绍MySQL字符串常用函数,本文结合实例代码给大家介绍的非常详细,对大家学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录mysql字符串常用函数一、获取二、大小写转换三、拼接四、截取五、比较、反转、替换六、去空白、填充MySQL字符串常用函数一、

C++中assign函数的使用

《C++中assign函数的使用》在C++标准模板库中,std::list等容器都提供了assign成员函数,它比操作符更灵活,支持多种初始化方式,下面就来介绍一下assign的用法,具有一定的参考价... 目录​1.assign的基本功能​​语法​2. 具体用法示例​​​(1) 填充n个相同值​​(2)

MySql基本查询之表的增删查改+聚合函数案例详解

《MySql基本查询之表的增删查改+聚合函数案例详解》本文详解SQL的CURD操作INSERT用于数据插入(单行/多行及冲突处理),SELECT实现数据检索(列选择、条件过滤、排序分页),UPDATE... 目录一、Create1.1 单行数据 + 全列插入1.2 多行数据 + 指定列插入1.3 插入否则更

PostgreSQL中rank()窗口函数实用指南与示例

《PostgreSQL中rank()窗口函数实用指南与示例》在数据分析和数据库管理中,经常需要对数据进行排名操作,PostgreSQL提供了强大的窗口函数rank(),可以方便地对结果集中的行进行排名... 目录一、rank()函数简介二、基础示例:部门内员工薪资排名示例数据排名查询三、高级应用示例1. 每

全面掌握 SQL 中的 DATEDIFF函数及用法最佳实践

《全面掌握SQL中的DATEDIFF函数及用法最佳实践》本文解析DATEDIFF在不同数据库中的差异,强调其边界计算原理,探讨应用场景及陷阱,推荐根据需求选择TIMESTAMPDIFF或inte... 目录1. 核心概念:DATEDIFF 究竟在计算什么?2. 主流数据库中的 DATEDIFF 实现2.1

MySQL中的LENGTH()函数用法详解与实例分析

《MySQL中的LENGTH()函数用法详解与实例分析》MySQLLENGTH()函数用于计算字符串的字节长度,区别于CHAR_LENGTH()的字符长度,适用于多字节字符集(如UTF-8)的数据验证... 目录1. LENGTH()函数的基本语法2. LENGTH()函数的返回值2.1 示例1:计算字符串

SpringBoot中如何使用Assert进行断言校验

《SpringBoot中如何使用Assert进行断言校验》Java提供了内置的assert机制,而Spring框架也提供了更强大的Assert工具类来帮助开发者进行参数校验和状态检查,下... 目录前言一、Java 原生assert简介1.1 使用方式1.2 示例代码1.3 优缺点分析二、Spring Fr

MySQL 中的 CAST 函数详解及常见用法

《MySQL中的CAST函数详解及常见用法》CAST函数是MySQL中用于数据类型转换的重要函数,它允许你将一个值从一种数据类型转换为另一种数据类型,本文给大家介绍MySQL中的CAST... 目录mysql 中的 CAST 函数详解一、基本语法二、支持的数据类型三、常见用法示例1. 字符串转数字2. 数字

Python内置函数之classmethod函数使用详解

《Python内置函数之classmethod函数使用详解》:本文主要介绍Python内置函数之classmethod函数使用方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地... 目录1. 类方法定义与基本语法2. 类方法 vs 实例方法 vs 静态方法3. 核心特性与用法(1编程客