c++11 指針空值


1. 引入nullptr的必要性:

典型的指針初始化是將其指向一個空的位置。比如:

int* my_ptr = 0;

int* my_ptr = NULL;

一般情況下,NULL是一個宏定義。

#undef NULL
#if defined(__cplusplus)
#define NULL 0
#else
#define NULL ((void*)0)
#endif

NULL可能被定義為字面常量0,或定義為無類型指針(void*)常量。

一下代碼顯示了使用NULL引起的意外的行為:

#include <stdio.h>

void f(char* c) {
  printf("invoke f(char*)\n");
}

void f(int i) {
  printf("invoke f(int)\n");
}

int main() {
  f(0);
  f(NULL);
  f((char*)0);

  return 0;
}

輸出為:

invoke f(int)

invoke f(int)    // NULL定義0造成的,字面常量0的類型既可以是一個整形,也可以是一個無類型指針(void*)

invoke f(char*)

2.nullptr定義:

typedef decltype(nullptr) nullptr_t;

關於nullptr的常見規則:

(1)所有定義nullptr_t類型的數據都是等價的,行為也是完全一致。

(2)nullptr_t類型數據可以隱式轉換成任意一個指針類型。

(3)nullptr_t類型數據不能轉換為非指針類型,即使使用reinterpret_cast<nullptr_t>()對的方式也不可以。

(4)nullptr_t類型數據不適用於算術運算表達式

(5)nullptr_t類型數據可以用於關系運算表達式,但僅能與nullptr_t類型數據或者指針類型數據進行比較。

#include <iostream>
#include <typeinfo>
using namespace std;

int main() {
  char* cp = nullptr;

  // 不可以轉換為整型
  // int n1 = nullptr;
  // int n2 = reinterpret_cast<int>(nullptr);


  //nullptr 與 nullptr_t 類型可以作比較
  nullptr_t nptr;
  if (nptr == nullptr) {
    cout << "nullptr_t nptr == nullptr" << endl;
  } else {
    cout << "nullptr_t nptr != nullptr" << endl;
  }

  if (nptr < nullptr) {
    cout << "nullptr_t nptr < nullptr" << endl;
  } else {
    cout << "nullptr_t nptr !< nullptr" << endl;
  }
//不可以進行算術運算
  // nullptr += 1;
  // nullptr * 5

  //以下可以正常運行
  sizeof(nullptr);
  typeid(nullptr);
  throw(nullptr);

  return 0;

}

 3. 規則討論

c++11標准中,nullptr類型數據所占用的內存空間大小跟void*相同。

sizeof(nullptr_t) == sizeof(void*)

nullptr是一個編譯時期的常量,其名字是一個編譯時期的關鍵字,能夠為編譯器所識別。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM