static_cast和dynamic_cast的區別,看完這篇你就懂了!
看了很久了這兩個到底是怎麼回事,終於今天幡然悔悟。還是要多讀書呀。
在C++ primer plus的15章第5節裡有介紹:
1 dynamic_cast :
dynamic_cast的語法:
dynamic_cast <type_name> (expression)
書上有兩個地方說了dynamic_cast的用途:
dynamic_cast運算子的用途是,使得能夠在類層次中進行向上轉換
僅當Low是High的可訪問基類時,下面的語句才會將一個Low*指標賦給pl:
pl = dynamic_cast<Low*>ph ; //說明下其中ph是派生類指標,pl是基類指標
否則,該語句將空指標賦值給pl
由此可見:使用dynamic_cast的用途是:實現安全的向上轉換,如果轉換不成功,那麼就會把被賦值的指標賦值為nullptr .
2 static_cast :
static_cast的語法:
static_cast <type_name> (expression)
主要用於將expression型別強制轉換為type_name誒型. 那麼我們需要知道如何判定轉換是否合法?
書上的轉換是否合法是這麼判定的,姑且稱為轉換合法原則:
當type_name可被隱式轉換為expression所屬的型別或者expression可被隱式轉換為type_name所屬的型別時,轉換是合法的,否則將出錯
摘錄出來就是:
以下條件主要滿足任一條,轉換合法:
1 ) type_name可被隱式轉換為expression所屬的型別 ;
2) expression可被隱式轉換為type_name所屬的型別.
我們結合書上給出的例子來看一下:
High 是一個基類 ,Low是 High類的一個派生類,有如下程式碼:
High bar; //基類
Low blow; //派生類
...
High *pb = static_cast<High *>(&blow); //blow是派生類,pb是基類的指標,因此這裡是向上轉換,合法
Low *pl = static_cast<Low *>(&bar); //bar是基類,pl是派生類指標,因此是向下轉換,合法
為什麼上述兩個轉換都是合法的呢?
其實原因就一條,我們都知道,在派生關係中, 基類的指標可以直接指向一個派生類的物件,這個過程不需要顯式轉換 ,因此結合上述的轉換合法原則,我們來分析一下上述兩句轉換的合法性:
1) High *pb = static_cast<High *>(&blow); // High *是 type_name ,&blow所屬的型別是Low * , 因為 High* 可以被隱式的轉換為Low* ,這符合轉換合法原則的前種情況 " type_name可被隱式轉換為expression所屬的型別" ,因此轉換合法;
2) Low *pl = static_cast<Low *>(&bar); // Low *是 type_name ,&bar所屬的型別是High * ,還是因為 High* 可以被隱式的轉換為Low* ,這符合轉換合法原則的後種情況 "expression可被隱式轉換為type_name所屬的型別",因此轉換合法.
因此,我們可以看到static_cast可以把原來只允許單向轉換的場景變成允許雙向轉換,類似的情況有:
1 一般來說,可以把任意的資料型別指標賦值給void *指標 ,但是不能把 void *指標賦值給任意資料型別的指標, 如果使用了static_cast ,那麼就可以實現把void * 賦值給 任意資料型別;
2 一般來說, 我們可以把int型別賦值給double型別,但是不能把 double型別的賦值給int型別 ,但如果使用了static_cast ,那麼就可以把double型別賦值給int型別
3 一般來說,我們可以把一個列舉型別enum直接賦值給int ,但是不能把int直接轉換為enum,但如果使用了static_cast ,那麼就可以實現這種轉換
....
類似的情況,大家可以繼續發散..總之 ,原則就一條 : 能不能合法轉換,主要取決於type_name和expression之間要存在任一方向的隱式轉換關係.
但是至於轉換後的內容是否安全,這是開發需要自行保證的,編譯器無法保證.
相關文章
- Sql Or NoSql,看完這一篇你就懂了SQL
- 看完這場直播,SASE你就懂了
- 運維到底是幹什麼的?看完這篇你就懂了運維
- 影響視訊推薦量的因素有哪些?這篇看完你就懂了
- 資料中臺還不清楚?看完Smartbi的這篇介紹你就懂了!
- BI如何能夠在銀行行業站足立腳的?看完這篇你就懂了!行業
- 資料安全“掃盲篇”,看完就懂了
- 資料分析報告沒有頭緒?看完Smartbi這篇介紹你就懂了!
- 0基礎如何開始學習Python?看完這篇就懂了!Python
- 成為優秀的資料分析師,需要具備哪些技能? 看完這篇你就懂了!
- 雲原生技術是什麼?看完這篇文章你就懂了
- 看完這篇 Linux 的基本操作你就會了!Linux
- 自定義ItemDecoration分割線的高度、顏色、偏移,看完這個你就懂了
- 什麼是“護網行動”?看完你就懂了
- Linux零拷貝技術,看完這篇文章就懂了Linux
- reinterpret_cast 和 static_cast 的區別AST
- 如何給bug定優先順序和嚴重程度?看完這裡就懂了
- HTML教程(看完這篇就夠了)HTML
- AR屬不屬於人工智慧?看完本文你就懂了人工智慧
- Hive(總)看完這篇,別說你不會Hive!Hive
- 看完這篇Linux基本的操作就會了Linux
- 網站CDN加速是什麼? 看完這篇你就明白了!網站
- 看完這篇,Promise面試就搞定了...Promise面試
- 搞懂鉤子方法和模板方法,看完這篇就夠了
- 管理者如何制定團隊目標?讀完這篇你就懂了.
- 教育培訓系統是怎麼樣執行的?看完這個就懂了!
- 為什麼嫁人就要嫁Linux運維工程師,看完你就懂了…Linux運維工程師
- 看完這篇 HashMap,和麵試官扯皮就沒問題了HashMap
- this到底指向啥?看完這篇就知道了!
- 蘋果iPhone Xs系列為什麼不值得買?看完這篇看完你就明白了蘋果iPhone
- 資料視覺化的基本流程是怎樣的,看完這篇你就明白視覺化
- static_cast與dynamic_cast到底是什麼?AST
- 銀行IT系統必經的松耦合,看完就懂了
- 執行緒池的基本原理,看完就懂了執行緒
- 【python】遞迴聽了N次也沒印象,讀完這篇你就懂了Python遞迴
- 共享WiFi專案到底怎麼做比較好?看完這篇文章就懂了!WiFi
- 【python】裝飾器聽了N次也沒印象,讀完這篇你就懂了Python
- 看完這篇 final、finally 和 finalize 和麵試官扯皮就沒問題了