十月讀書心得

1.sizeof與strlen的區別。

#include <iostream>
using namespace std;
void main()
{cout << sizeof("hello") << endl;}
答案: 6

原因: “hello”={‘h’,'e','l','l','o','\0'};共六個字節。

那么sizeof與strlen有什么區別呢?

總結起來:

1).?sizeof 是運算符,在編譯時其值在編譯時即計算好了,參數可以是數組、指針、類型、對象、函數等。

? ? 而sgtrlen是函數,在運行時才知道大小?由于在編譯時計算,因此sizeof不能用來返回動態分配的內存空間的大小。實際上,用sizeof來返回類型以及靜態分配的對象、結構或數組所占的空間,返回值跟對象、結構、數組所存儲的內容沒有關系。

2).sizeof計算的是最大對象的字節大小,而strlen是計算實際存儲的字符個數。

3).sizeof的參數可以是數組、指針、類型、函數,而strlen只能是字符串指針或者數組。

2.內存空間分幾部分:BSS段、代碼段、數據段,棧,堆?

下面我們來簡單歸納一下進程對應的內存空間中所包含的5種不同的數據區都是干什么的。

BSS段:BSS段(bss segment)通常是指用來存放程序中未初始化的全局變量的一塊內存區域。BSS是英文Block Started by Symbol的簡稱。BSS段屬于靜態內存分配。

數據段:數據段(data segment)通常是指用來存放程序中已初始化的全局變量的一塊內存區域。數據段屬于靜態內存分配。

代碼段:代碼段(code segment/text segment)通常是指用來存放程序執行代碼的一塊內存區域。這部分區域的大小在程序運行前就已經確定,并且內存區域通常屬于只讀, 某些架構也允許代碼段為可寫,即允許修改程序。在代碼段中,也有可能包含一些只讀的常數變量,例如字符串常量等

堆(heap):堆是用于存放進程運行中被動態分配的內存段,它的大小并不固定,可動態擴張或縮減。當進程調用malloc等函數分配內存時,新分配的內存就被動態添加到堆上(堆被擴張);當利用free等函數釋放內存時,被釋放的內存從堆中被剔除(堆被縮減)

棧(stack):棧又稱堆棧, 是用戶存放程序臨時創建的局部變量,也就是說我們函數括弧“{}”中定義的變量(但不包括static聲明的變量,static意味著在數據段中存放變量)。除此以外,在函數被調用時,其參數也會被壓入發起調用的進程棧中,并且待到調用結束后,函數的返回值也會被存放回棧中。由于棧的先進后出特點,所以棧特別方便用來保存/恢復調用現場。從這個意義上講,我們可以把堆棧看成一個寄存、交換臨時數據的內存區。

它是由操作系統分配的,內存的申請與回收都由OS管理。

3.運算符和函數的區別

(1)語法形式上會有區別;
(2)運算符只能重載,不能自定義,函數的名字隨便你起,只要是個標志符就行;但運算符不行,比如,你無法仿照其它語言的符號,自己定義一個乘方運算符“**”。
(3)任何函數都可以重載或者覆蓋,但通常你不能改變運算符作用于內置類型的行為,比如你不能通過重載“operator+”,讓3?+?2產生出6來。

4.C++中malloc/free與new/delete的區別及內存分配失敗錯誤處理

首先談談C/C++內存分配失敗錯誤處理
一、C語言中的malloc/calloc/realloc/valloc/alloca/memalign函數:
這樣的內存分配函數在內存分配失敗時都返回空指針,因此,在調用返回時,檢查返回值的方法比較簡單,只需要與空指針比較即可;
如:
char* p = (char*)malloc(1204);
if(p == NULL)
{
//error handle;
};
char* pp = (char*)calloc(3,1024);
if(pp == NULL)
{
//error handle;
};
二、C++中的new操作符:
C++中的new操作符在分配內存失敗時默認的操作是拋出一個內置的異常,而并不是直接返回空指針;這樣的話,再把返回值與空指針比較,就沒有什么意義了;因為,C++拋出異常之后,就直接跳出new操作符所在的那一行代碼,而不再執行后續的代碼行了,所以,對new操作符返回值的判斷代碼就執行不到了;當然,標準C++也提供了抑制拋出異常的方法,使之不再排除內存分配失敗的異常,轉而直接返回空指針,這是因為比較古老的編譯器里面可能沒有異常處理機制,不能捕獲到異常;如:
int* p = new int[SIZE];
if(p == 0) //檢查p是否是空指針;這個判斷沒有意義;
{
return -1;
}
所以,在C++中有兩種方法來處理new操作符分配內存失敗的錯誤;
1、通過捕獲new操作符拋出的異常:
char* p = NULL;
try
{
p = new char[1024];
}
catch(const std::bad_alloc& ex)
{
//exception handle;
return -1;
}
2、抑制異常的拋出:
char* p = NULL;
p = new(std::nothrow)char[1024]; //這樣的話,如果new分配內存失敗,就不會再拋出異常,而是返回空指針了;
if(p == NULL) //這樣的判斷就有意義了;
{
//error handle;
return -1;
}
三、執行free或delete釋放內存之后,還需要做什么?
被free()掉的指針,我們通常叫野指針,野指針是非常危險的哦,可能導致多次釋放內存或者對野指針進行訪問,
這兩種情況都可能導致嚴重的安全風險。
最好的也是最簡單的解決辦法就是在釋放后,把指針設置為NULL或者指向另一個合法的對象。
就像這樣:
free(ptr);
ptr = NULL;
測試程序:

#include<iostream>  
using namespace std;  int main()  
{  int *p = new int[5];  //_________使用new沒有必要檢查內存分配失敗  delete p;  //此處為了驗證釋放p指針指向的內存之后,指針是否為NULL。答案是不會輸出Yes  if (p == NULL)  cout<<"Yes"<<endl;  //為了避免“野指針”,必須給指針p重新賦值。此處置為NULL  p = NULL;  int *pp = (int *)malloc(sizeof(int)*5);  //使用malloc有必要檢測  if (pp == NULL)  {  cout<<"error"<<endl;  }  free(pp);  pp = NULL;  return 0;  
}  

下面說說malloc/free與new/delete的區別及使用要點

相同點:都可用于申請動態內存和釋放內存
不同點:
(1)操作對象有所不同。
malloc與free是C++/C 語言的標準庫函數,new/delete 是C++的運算符。對于非內部數據類的對象而言,光用maloc/free 無法滿足動態對象的要求。對象在創建的同時要自動執行構造函數, 對象消亡之前要自動執行析構函數。由于malloc/free 是庫函數而不是運算符,不在編譯器控制權限之內,不能夠把執行構造函數和析構函數的任務強加malloc/free。
(2)用法上也有所不同。
函數malloc 的原型如下:
void * malloc(size_t size);
用malloc 申請一塊長度為length 的整數類型的內存,程序如下:
int *p = (int *) malloc(sizeof(int) * length);
我們應當把注意力集中在兩個要素上:“類型轉換”和“sizeof”。
1、malloc 返回值的類型是void *,所以在調用malloc 時要顯式地進行類型轉換,將void * 轉換成所需要的指針類型。
2、 malloc 函數本身并不識別要申請的內存是什么類型,它只關心內存的總字節數。
函數free 的原型如下:
void free( void * memblock );
為什么free 函數不象malloc 函數那樣復雜呢?這是因為指針p 的類型以及它所指的內存的容量事先都是知道的,語句free(p)能正確地釋放內存。如果p 是NULL 指針,那么free
對p 無論操作多少次都不會出問題。如果p 不是NULL 指針,那么free 對p連續操作兩次就會導致程序運行錯誤。

new/delete 的使用要點:
運算符new 使用起來要比函數malloc 簡單得多,例如:
int *p1 = (int *)malloc(sizeof(int) * length);
int *p2 = new int[length];
這是因為new 內置了sizeof、類型轉換和類型安全檢查功能。對于非內部數據類型的對象而言,new 在創建動態對象的同時完成了初始化工作。如果對象有多個構造函數,那么new 的語句也可以有多種形式。
如果用new 創建對象數組,那么只能使用對象的無參數構造函數。例如
Obj *objects = new Obj[100]; // 創建100 個動態對象
不能寫成
Obj *objects = new Obj[100](1); // 創建100 個動態對象的同時賦初值1
在用delete 釋放對象數組時,留意不要丟了符號‘[]’。例如
delete []objects; // 正確的用法
delete objects; // 錯誤的用法
后者相當于delete objects[0],漏掉了另外99 個對象。
/
1、new自動計算需要分配的空間,而malloc需要手工計算字節數
2、new是類型安全的,而malloc不是,比如:
int* p = new float[2]; // 編譯時指出錯誤
int* p = malloc(2*sizeof(float)); // 編譯時無法指出錯誤
new operator 由兩步構成,分別是 operator new 和 construct
3、operator new對應于malloc,但operator new可以重載,可以自定義內存分配策略,甚至不做內存分配,甚至分配到非內存設備上。而malloc無能為力
4、new將調用constructor,而malloc不能;delete將調用destructor,而free不能。
5、malloc/free要庫文件支持,new/delete則不要。
/
1、本質區別
malloc/free是C/C++語言的標準庫函數,new/delete是C++的運算符。
對于用戶自定義的對象而言,用maloc/free無法滿足動態管理對象的要求。對象在創建的同時要自動執行構造函數,對象在消亡之前要自動執行析構函數。由于malloc/free是庫函數而不是運算符,不在編譯器控制權限之內,不能夠把執行構造函數和析構函數的任務強加于malloc/free。因此C++需要一個能完成動態內存分配和初始化工作的運算符new,以及一個能完成清理與釋放內存工作的運算符delete。

class Obj  
{  
public:  Obj( )   { cout  <<  "Initialization"  <<  endl; }  ~ Obj( )  { cout  <<  "Destroy" <<  endl; }  void Initialize( )  { cout  <<  "Initialization"  <<  endl; }  void  Destroy( )  { cout  <<  "Destroy"  <<  endl; }  
}obj;  void  UseMallocFree( )  
{  Obj   * a  =  (Obj  *) malloc( sizeof ( obj ) );      //  allocate memory   a -> Initialize();                                    //  initialization  // …   a -> Destroy();                                        // deconstruction   free(a);                                               // release memory  
}  void  UseNewDelete( void )  
{  Obj   * a  =   new  Obj;                                             // …   delete a;   
}  

類Obj的函數Initialize實現了構造函數的功能,函數Destroy實現了析構函數的功能。函數UseMallocFree中,由于malloc/free不能執行構造函數與析構函數,必須調用成員函數Initialize和Destroy來完成“構造”與“析構”。所以我們不要用malloc/free來完成動態對象的內存管理,應該用new/delete。由于內部數據類型的“對象”沒有構造與析構的過程,對它們而言malloc/free和new/delete是等價的。

2、聯系
既然new/delete的功能完全覆蓋了malloc/free,為什么C++還保留malloc/free呢?因為C++程序經常要調用C函數,而C程序只能用malloc/free管理動態內存。如果用free釋放“new創建的動態對象”,那么該對象因無法執行析構函數而可能導致程序出錯。如果用delete釋放“malloc申請的動態內存”,理論上講程序不會出錯,但是該程序的可讀性很差。所以new/delete、malloc/free必須配對使用。

5.空類的大小

這就是實例化的原因(空類同樣可以被實例化),每個實例在內存中都有一個獨一無二的地址,為了達到這個目的,編譯器往往會給一個空類隱含的加一個字節,這樣空類在實例化后在內存得到了獨一無二的地址,所以空類所占的內存大小是1個字節。

#include<iostream>
using namespace std
class a{};
int main()
{
cout<<"sizeof(a)="<<sizeof(a)<<endl;
return 0;
}
程序執行的輸出結果為:
sizeof(a)=1
以上程序驗證了空類所占內存為1個字節。
6.大小端

#include<iostream>
using namespace std;void main()
{
const char* p="\x12\x34\x56\x78";
printf("0x%x",*(int*)p);}
答案:0x78563412請按任意鍵繼續. . .
原因:








參考文獻:

1.《Sizeof與Strlen的區別與聯系》

2.《 sizeof和strlen之比較》

3.《C++中malloc/free與new/delete的區別及內存分配失敗錯誤處理》




本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/259104.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/259104.shtml
英文地址,請注明出處:http://en.pswp.cn/news/259104.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

nginx php-fpm 輸出php錯誤日志(轉)

nginx是一個web服務器&#xff0c;因此nginx的access日志只有對訪問頁面的記錄&#xff0c;不會有php 的 error log信息。 nginx把對php的請求發給php-fpm fastcgi進程來處理&#xff0c;默認的php-fpm只會輸出php-fpm的錯誤信息&#xff0c;在php-fpm的errors log里也看不到ph…

protobuf的安裝和使用

以下全部基于win7系統。 protobuf是什么&#xff0c;有什么用網上說的已經很多了。這里就是說一下怎么使用。就當給自己做個筆記吧。 .proto文件的語法什么的也請網上查看&#xff0c;挺多的。 第一步&#xff1a; 下載protoc.exe 和 protobuf-java-2.4.1.jar。這里要注意版本區…

win7優化設置_win7藍牙怎么打開?

當電腦需要連接藍牙設備的時候&#xff0c;就需要打開藍牙設置才行。鑒于一些win7的用戶還不知道藍牙功能在哪&#xff0c;win7藍牙怎么打開&#xff0c;故系統圣地分享本篇教程。1、win7藍牙怎么打開?首先要你的電腦支持藍牙功能。如果你的電腦有藍牙功能的話那么在電腦的右下…

Struts2 通配符

在配置<action …./>元素時&#xff0c;需要指定name,class和method屬性&#xff0c;這三個屬性都支持通配符。 例如&#xff1a; 1.<action name ”*Action” class “student.RegisterAction” method “{1}”> 如果用戶請求的URL為loginAction.action,則調用…

Doxygen從零學起———安裝和配置

Doxygen可以為多種語言生成說明文檔&#xff08;從程序的源代碼中提取其中按照約定格式寫的注釋中提取信息&#xff09; 例如C, Objective-C, C#, C, PHP, Python, IDL (Corba, Microsoft, and UNO/OpenOffice flavors), Fortran, VHDL, Tcl, D ,從這期開始&#xff0c;我將系…

JAVA Drp項目實戰—— Unable to compile class for JSP 一波三折

交代下背景。電腦系統是64位的&#xff0c;用的是64位的Tomcat。安裝是32位的Myeclipse10&#xff0c;java環境也是32位的。Tomcat在開始啟動時會報這樣一個錯誤&#xff0c;“Cant load IA 64-bit .dll on a AMD32-bit platform”。可是不耽誤使用&#xff0c;近期在敲Drp項目…

Java中的ClassLoader

Java中類的加載過程&#xff08;如Dog類&#xff09;&#xff1a; 通過類型信息定位Dog.class文件。載入Dog.class文件&#xff0c;創建相應的Class對象。執行父類的靜態字段定義時初始化語句和父類的靜態初始化塊。執行子類的靜態字段定義時初始化語句和子類的靜態初始化塊。當…

excel刪除無盡空白行_excel如何批量刪除空白行 巧用 ctrl+G 只需1秒 最常用的技巧...

工作中我們使用excel通常都會遇到這種情況&#xff0c;就是表格中有很多多余的空行。我們需要把多余的空行刪除。 如果空行只有一兩行的話&#xff0c;可以把鼠標放在空白行上&#xff0c;然后點擊鼠標右鍵&#xff0c;在彈出的菜單中選擇刪除菜單。 在彈出的刪除確定窗口中&am…

Doxygen for C++使用說明——注釋代碼一

寫這一節的時候&#xff0c;我在想網上有眾多的參考文獻&#xff0c;外加官網上的&#xff0c;要是我再將它們重復一遍&#xff0c;也沒什么意思。網上資料很多&#xff0c;但是他們有一個共同的缺點是都是羅列用法&#xff0c;然后顯示效果。這些都是比較散的&#xff0c;我想…

DevOps的前世今生

2019獨角獸企業重金招聘Python工程師標準>>> 目前在國外&#xff0c;互聯網巨頭如Google、Facebook、Amazon、LinkedIn、Netflix、Airbnb&#xff0c;傳統軟件公司如Adobe、IBM、Microsoft、SAP等&#xff0c;亦或是網絡業務非核心企業如蘋果、沃爾瑪、索尼影視娛樂…

【轉】最牛B的編碼套路

最近&#xff0c;我大量閱讀了Steve Yegge的文章。其中有一篇叫“Practicing Programming”&#xff08;練習編程&#xff09;&#xff0c;寫成于2005年&#xff0c;讀后令我驚訝不已&#xff1a; 與你所相信的恰恰相反&#xff0c;單純地每天埋頭于工作并不能算是真正意義上的…

ecshop 廣告設置

最近公司準備做個商城&#xff0c;讓我從JAVA轉過去&#xff0c;好吧&#xff0c;先看下吧&#xff0c;反正也得做。接到手里的是一套已經成型的模板&#xff0c;但是二次開發必須得了解下機制、文件、響應、設置什么的&#xff0c;也是個新手&#xff0c;寫點東西給后面更新的…

linux 信號_Linux信號機制

信號就是一條消息&#xff0c;通知進程系統中發生了什么事&#xff0c;每種信號都對應著某種系統事件。一般的底層硬件異常是由內核的異常處理程序處理的&#xff0c;它對用戶進程來說是透明的。而信號機制&#xff0c;提供了一種方法通知用戶進程發生了這些異常。例如&#xf…

DOxygen for C++使用說明——添加數學公式

公式 Doxygen允許你把 公式顯示在最終的輸出中&#xff08;這個功能僅限于HTML和輸出&#xff09;.為了可以在HTML documentation顯示公式&#xff08;轉化為圖片&#xff09;&#xff0c;你必須安裝以下軟件&#xff1a; latex: 編譯器, 被用來解析公式, 首先提取公式寫到一…

VC2010下Qt5的中文亂碼問題

要搞清楚這個問題&#xff0c;先要弄明白編碼。但是編碼問題實在太復雜&#xff0c;這里肯定講不開。 我先找一個例子&#xff0c;比如&#xff1a;“中文” 的 Unicode 碼點/UTF8編碼/GBK 分別是多少。 先去這個網站&#xff0c;輸入 “中文” 查詢對應的 Unicode 碼點/UTF8編…

Tomcat 的 DefaultServlet

問題描述&#xff1a; 群里有人測試 Spring MVC&#xff0c;沒有配置任何Controller&#xff0c;只配置了一個view resolver&#xff0c;指定了前綴后綴。 然后&#xff0c;他問的是 當訪問 localhost:8080/test 的時候&#xff0c;為什么會被重定向到 localhost:8080/test/ &a…

Python學習(七)面向對象 ——封裝

Python 類的封裝 承接上一節&#xff0c;學了Student類的定義及實例化&#xff0c;每個實例都擁有各自的name和score。現在若需要打印一個學生的成績&#xff0c;可定義函數 print_score() 該函數為類外的函數&#xff0c;如下&#xff1a; 1 class Student(object):2 def …

spss練習數據_SPSS篇——如何在成千上百萬個數據中標識重復個案

本文就帶大家來學習一個小技巧&#xff0c;如何運用SPSS標識重復個案。我們都知道在Excel中&#xff0c;通常會用到“篩選”功能來選出指定條件相同的單元格。那么在SPSS中&#xff0c;如何在成千上百萬個數據中篩選出重復的個案呢&#xff1f; 小編就是要告訴你&#xff0c;幾…

DOxygen for C++使用說明——Markdown支持

自Doxygen 版本1.8.0&#xff0c;Markdown被引進。 接下來&#xff0c;我們將先簡單介紹標準的Markdown語法&#xff0c;讀者可以進入Markdown官網查詢更詳細的細節。然后討論一下Doxygen支持的Markdown擴展&#xff0c;最后討論一下Doxygen對Markdown標準的實現細節。 Stand…

方程式漏洞之復現window2008/win7 遠程命令執行漏洞

前幾天就想寫的&#xff0c;因為一些緣故就沒寫。此次是在外網環境下進行的。大家在內網中也一個樣。 方法&#xff1a; 使用Eternalblue模塊&#xff0c;劍測是否有漏洞然后msf生成一個dll直接反彈shell. PS&#xff1a;win版本的不知道緣何生成出來的dll是0kb 我就在自己本地…