如果不为null,则为指针赋值

时间:2014-07-31 18:57:13

标签: c++ pointers null

我有一个整数指针作为默认函数参数。如果它不为null,我想分配一些值,也许是每200行中的第10行。在每次分配之前进行标准检查,我的代码很容易变大和难以阅读。 (我的意思是源文件长度和可读性,而不是二进制大小。)

替换这个是好的做法:

// Previous statement
// Use to put empty line here
if(ptr)
    *ptr = val;
// Empty line also here
// Next statement

用这个:

// Previous statement
assignIfNotNull(ptr, val);
// Next statement

并将if放入功能?

inline void assignIfNotNull(int *ptr, int val)
{
    if(ptr)
        *ptr = val;
}

现在,我似乎很细致,但每次使用会节省3行。也许不是我编程风格中最糟糕的事情,因为我独自学习即兴创作。我想压制它,要求并跟上标准。 (我无法在任何地方找到它。)

提前致谢。

2 个答案:

答案 0 :(得分:1)

C# null coalescing operator equivalent for c++几乎准确地问你的问题,但不要指望找到一些突破性的解决方案 - 三元运算符,模板和宏只有一些变化:

ptr = (ptr != null ? ptr : MY_DEFAULT)

//------------------- or as function
template<class T>
GetValueOrDefault(T* value, T* defaultValue) // or put your own types
{
    return value != null ? value : defaultValue;
}

ptr = GetValueOrDefault(ptr, MY_DEFAULT);

//------------------- or as macro

#define GET_VALUE_OR_DEFAULT(value, defaultValue) (value != null ? value : defaultValue)

ptr = GET_VALUE_OR_DEFAULT(ptr, MY_DEFAULT);

//------------------- or like this macro

#define VALUE_OR_DEFAULT(value, defaultValue) value = (value != null ? value : defaultValue)

VALUE_OR_DEFAULT(ptr, MY_DEFAULT);

但是你应该考虑一些观点:

  1. 当它不存在时,不要想象一个问题 - 对于某些API来说,很多检查和重新初始化都是完全可行的 - 只需看看WINAPI
  2. 您确定应该覆盖此变量吗?可能是你 可以重写您的函数或API以不覆盖它。
  3. 您也可以考虑使用一些临时变量来代替 ptr - 它无法解决问题,只需将其颠倒过来,但是 这可能会提高你的整体可理解性 功能和删除检查:

      char* tempPtr = ptr;
      retCode = RandomlyNullifyThePtr(&tempPtr); // RandomlyNullifyThePtr can nullify the ptr it gets ,
      // but it won't nullify the ptr in calling function.
    
  4. 如果您在保持整个功能时遇到问题 良心然后它是直接的迹象,它应该被重构 - 分成小块,这样的检查可能会变成 不必要:

      retCode = CompletePart1(ptr); // CompletePart1 can nullify the ptr it gets, 
      // but it won't nullify the ptr in calling function.
      ...
      retCode = CompletePart2(ptr);
    

答案 1 :(得分:1)

你可以去:

T dummy;
if ( !ptr ) 
    ptr = &dummy;

一开始;然后您可以安全地编写*ptr = whatever;,而无需进行空检查。

如果ptr的原始值很重要,您可以调用参数orig_ptr或其他内容。