精华内容
下载资源
问答
  • assert函数

    2012-03-10 22:21:08
    介绍assert函数的具体用法 方便初学者学习
  • 最初的出发点都是为了方便调试而设计的,但是最近越来越多的开发者不分测试环境和正式环境滥用assert函数,引发了我对广大程序员朋友的担忧,故写此篇文章普及assert函数常识,避免各位朋友滥用assert函数。...

    assert函数广泛在java、Python、PHP、C语言中存在,都有统一的意义,用业界语言称之为"断言"。最初的出发点都是为了方便调试而设计的,但是最近越来越多的开发者不分测试环境和正式环境滥用assert函数,引发了我对广大程序员朋友的担忧,故写此篇文章普及assert函数常识,避免各位朋友滥用assert函数。

    简单的概况在各个语言中assert函数的意义:如果表达式的值为假,整个程序将退出,并输出一条错误信息。如果表达式的值为真则继续执行后面的语句。

    dad9449aa07e2230a5413931430b6559.pngassert函数

    assert函数Java中,断言关键字是从JAVA SE 1.4引入的。为了避免在旧版本的Java代码中使用assert关键字导致的错误,Java在执行时默认不启动断言检查(此时,所有断言语句都将被忽略!),如果您想打开断言检查,您需要使用switch-enable断言或-ea来打开它。

    在C中,assert的作用是先计算表达式 expression ,如果其值为假(即为0),那么它先向stderr打印一条出错信息,然后通过调用 abort 来终止程序运行

    75da08b8c2de52c5cc0e4a5448fee76c.pngassert函数

    Python中断言函数作用:断言函数是对表达式布尔值的判断,要求表达式计算值必须为真。可用于自动调试。

    如果表达式为假,触发异常;如果表达式为真,不执行任何操作。

    断言函数形式:

    assert(condition)

    if not condition:

    raise AssertionError()

    PHP中assert这个函数在php语言中是用来判断一个表达式是否成立。返回true or false;例如

    $s = 123;

    assert("is_int($s)");

    ?>

    从这个例子可以看到字符串参数会被执行,这跟eval()类似。不过eval($code_str)只是执行符合php编码规范的$code_str。

    已放弃使用assert()的原因是,频繁的调用会极大的影响程序的性能,增加额外的开销。在调试结束后,应当禁用assert调用。

    Assert用于避免明显的错误,而不是处理异常。错误和异常是不同的。错误不应该发生,例外是不可避免的。c语言异常可以通过条件判断来处理。其他语言有自己的异常处理机制。

    使用assert的一个非常简单的规则是在方法或函数的开头使用它。如果你在一个方法中使用它,你需要仔细考虑它是否合适。在该方法开始时,功能过程还没有开始,并且在功能过程执行期间发生的几乎所有问题都是直接抛异常的。

    为assert是用于调试测试程序的,并且不用于正式的生产环境,所以应该考虑用一个更好的测试JUint来代替它。JUint提供了比assert键更多的功能。当然,调试和测试可以通过集成开发环境调试来进行。

    因此,应该避免在各种语言中使用assert函数,除非某一天assert函数变得无比的强大,不再区分测试环境和正式环境的切换,此时可以考虑这一点。比较一下断言能给你带来多少好处和麻烦。这是我们选择是否使用它的原则。

    好了,先生们女士们,此次关于assert函数就分享到这里!

    展开全文
  • ASSERT函数

    2016-10-25 14:00:53
    ASSERT函数supreme42的博客http://blog.csdn.net/supreme42/article/details/7021518>assert宏的原型定义在中,其作用是如果它的条件返回错误,则终止程序执行,原型定义: #include void assert( int expression )...

    ASSERT函数<转自supreme42的博客http://blog.csdn.net/supreme42/article/details/7021518>


    assert宏的原型定义在<assert.h>中,其作用是如果它的条件返回错误,则终止程序执行,原型定义: 
    #include <assert.h> 
    void assert( int expression ); 

    assert的作用是现计算表达式 expression ,如果其值为假(即为0),那么它先向stderr打印一条出错信息, 
    然后通过调用 abort 来终止程序运行。

    提高程序健壮性之assert使用

    编写能正常运行的程序很难;编写在错误情况下仍然表现的很“优雅”的程序更难。这篇文章将和大家讨论一些编程技巧,可以使我们在运行中的程序中早点发现错误,检测和从问题中恢复。那就先讨论下断言(assert)的使用吧。

    在编码时,有一个好的目标应该时刻铭记在心,那就是:应该想办法让bug或者异常错误尽早使得程序down掉,或者出现错误。因为这样可以帮助你在开发和测试阶段尽快找出bug。有一些错误不会无缘无故的暴露自己,往往是产品都到了客户手上,这些错误才会显现出来。

    一个最简单的检查异常条件的方法是使用标准C的assert宏,它的参数是一个bool表达式。当表达式为假时,程序会退出。在退出之前打印错误消息,包括源文件,行号,和表达式本身。断言非常有用,它提供了一个作用于程序内部的广泛的一致性检查方法。例如,使用断言测试函数参数的有效性,测试异常的返回值等等。

    每一个断言的使用不仅提供了一个程序运行时的条件检查,也像一个对源代码级别的程序操作的说明性文档。如果你的程序包含了一个断言,也就是告诉那些阅读你源代码的人,在你的源代码中,在程序的这一点,这个条件应该为真,如果不为真,那就是一个bug。

    当然,在追求性能的代码中,使用assert会降低程序性能。但是你放心,在编译时加入NDEBUG参数编译器就可以对assert进行预处理,从而移除它。正因为在预处理时可能移除assert,那你使用时就得小心了。什么时候用,什么时候不用就成了一个问题。通常,你不应该在assert内部调用函数,定义变量,或者使用改变值的操作符,如++。

    我们假设你这样使用了:

    for (i = 0; i &lt;= 100; ++i) assert (do_something () == 0);

    然后,你可能会发现这样会使得性能大大降低,从而在创新编译使使用NDEGUG参数。这将移除整个assert宏,这就将do_something( )也被移除了,再也不被调用。为了纠正错误,你应该这样写:

    for (i = 0; i &lt;= 100; ++i) { int status = do_something (); assert (status == 0); }

    另外应该铭记在心的是,不要用assert去检查无效的输入。用户可不喜欢自己在输入时程序直接退出,即便是输入错误,程序最好也有友好的响应。所以,你应该对无效输入进行检查,并输出一些有用的提示信息。只在程序运行中进行内部检查时使用断言。

    在这里,我会给出一些比较好的在程序中使用assert的地方:

    (1)空指针检查。例如,针对一个函数的参数进行空指针检查。你可以这样使用:assert (pointer != NULL);,产生的错误会像这样:Assertion ‘pointer != ((void *)0)’ failed。这样,当出现空指针时,你的程序就会退出,并很好的给出错误信息。

    (2)检查函数参数的值。例如,如果一个函数只能在它的一个参数foo为正值的时候被调用,你可以在函数开始时这样写:assert (foo > 0);,这将帮助你检测函数的错误使用,这也给源代码阅读者很清晰的印象,那就是在这里对函数的参数值有限制。

    说了这么多,行动起来吧,大胆的在你的程序中使用断言。




    ---------------------------------------------------------------   

    ASSERT()是一个调试程序时经常使用的宏,在程序运行时它计算括号内的表达式,如果表达式为FALSE  (0),  程序将报告错误,并终止执行。如果表达式不为0,则继续执行后面的语句。这个宏通常原来判断程序中是否出现了明显非法的数据,如果出现了终止程序以免导致严重后果,同时也便于查找错误。   

    ASSERT只有在Debug版本中才有效,如果编译为Release版本则被忽略。   
    ---------------------------------------------------------------   

    ASSERT宏定义如下   

    #define  ASSERT(f)  \   
    do  \   
    {  \   
          if  (!(f)  &&  AfxAssertFailedLine(THIS_FILE,  __LINE__))  \   
                  AfxDebugBreak();  \   
    }  while  (0)  \

    ASSERT(逻辑表达式)   

    如果括号中的逻辑表达式值为假的话,会弹出调试命令窗口,提示具体在哪个文件的哪一行发生了断言错误!   
    ---------------------------------------------------------------   

    ASSERT   
    Evaluates  an  expression,  and  displays  a  diagnostic  message  if  the  expression  is  FALSE.  Ignored  in  retail  builds.   
    Syntax   
    ASSERT(   
          cond   
    );

    Parameters   

    cond   

    Expression  to  evaluate.   

    Remarks   

    In  debug  builds,  if  the  expression  is  FALSE,  this  macro  displays  a  message  box  with  the  text  of  the  expression,  the  name  of  the  source  file,  and  the  line  number.  The  user  can  ignore  the  assertion,  enter  the  debugger,  or  quit  the  application.   

    Example   

    ASSERT(rtStartTime  <=  rtEndTime);   


    ---------------------------------------------------------------   

    断言(ASSERT)的使用,方法很简单。为什么要用,初学者可能比较迷惑。   
    契约式编程讲的比较清楚,建议可以先看看这类书。   
    一个函数由前置条件、后置条件和不变式组成。在VC中,我们可以通过断言来保证这三个条件。可以大大提高了软件的质量。   
    ---------------------------------------------------------------   

    如果ASSERT()中的条件不成立(比如  ASSERT(0)  ;    ),会弹出一个比较吓人的对话框。   

    点击重试,可以到达  ASSERT  断言不成立的那一行,   

    此时可以在watch窗口查看变量值,找出出错的原因。   


    展开全文
  • assert 函数

    2017-01-16 10:44:19
    assert()函数用法总结  assert宏的原型定义在中,其作用是如果它的条件返回错误,则终止程序执行,原型定义: #include assert.h> void assert( int expression );  assert的作用是现计算表达式 ...

    assert()函数用法总结

      assert宏的原型定义在<assert.h>中,其作用是如果它的条件返回错误,则终止程序执行,原型定义:

    #include <assert.h>
    void assert( int expression );

      assert的作用是现计算表达式 expression ,如果其值为假(即为0),那么它先向stderr打印一条出错信息,然后通过调用 abort 来终止程序运行。请看下面的程序清单badptr.c:

    复制代码
    #include <stdio.h>
    #include <assert.h>
    #include <stdlib.h>
    int main( void )
    {
           FILE *fp;
        
           fp = fopen( "test.txt", "w" );//以可写的方式打开一个文件,如果不存在就创建一个同名文件
           assert( fp );                           //所以这里不会出错
           fclose( fp );
        
           fp = fopen( "noexitfile.txt", "r" );//以只读的方式打开一个文件,如果不存在就打开文件失败
           assert( fp );                           //所以这里出错
           fclose( fp );                           //程序永远都执行不到这里来
           return 0;
    }
    复制代码

    [root@localhost error_process]# gcc badptr.c 
    [root@localhost error_process]# ./a.out 
    a.out: badptr.c:14: main: Assertion `fp' failed.

      已放弃使用assert()的缺点是,频繁的调用会极大的影响程序的性能,增加额外的开销。在调试结束后,可以通过在包含#include <assert.h>的语句之前插入 #define NDEBUG 来禁用assert调用,示例代码如下:

    #include <stdio.h>
    #define NDEBUG
    #include <assert.h>


    用法总结与注意事项:

      1)在函数开始处检验传入参数的合法性如:

    复制代码
    int resetBufferSize(int nNewSize)
    {
      //功能:改变缓冲区大小,
      //参数:nNewSize 缓冲区新长度
      //返回值:缓冲区当前长度 
      //说明:保持原信息内容不变     nNewSize<=0表示清除缓冲区
      assert(nNewSize >= 0);
      assert(nNewSize <= MAX_BUFFER_SIZE);
      ...
    }
    复制代码

      

      2)每个assert只检验一个条件,因为同时检验多个条件时,如果断言失败,无法直观的判断是哪个条件失败,如:

      不好:

    assert(nOffset>=0 && nOffset+nSize<=m_nInfomationSize);

      好:

    assert(nOffset >= 0);
    assert(nOffset+nSize <= m_nInfomationSize);

      3)不能使用改变环境的语句,因为assert只在DEBUG个生效,如果这么做,会使用程序在真正运行时遇到问题,如:

      错误:

    assert(i++ < 100);

      这是因为如果出错,比如在执行之前i=100,那么这条语句就不会执行,那么i++这条命令就没有执行。

      正确:

     assert(i < 100);
     i++;

      4)assert和后面的语句应空一行,以形成逻辑和视觉上的一致感。

      5)有的地方,assert不能代替条件过滤。

    展开全文

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 7,139
精华内容 2,855
关键字:

assert函数