1. 程式人生 > >C#中string,String,StringBuffer,StringBuilder的學習筆記

C#中string,String,StringBuffer,StringBuilder的學習筆記

 string是基本型別,是不可改變物件,string s1="test";實際上是建立了一個名字為s1的string型別物件,系統為s1建立足夠的記憶體來儲存它,s1+="ceshi",並不是在s1所指向的地址內新增字串“cehsi”,而是新建了一個“testceshi”字串並將s1指向這個新的字串,系統將原來的“test”登出掉,如果頻繁的進行字串的修改會嚴重影響系統性能。

在字串處理中C#提供了String、StringBuffer、StringBuilder三個類。

1、  三者在執行速度方面的比較:StringBuilder >StringBuffer > String

String一旦賦值或例項化後就不可更改,如果賦予新值將會重新開闢記憶體地址進行儲存。

而StringBuffer類使用append和insert等方法改變字串值時只是在原有物件儲存的記憶體地址上進行連續操作,減少了資源的開銷。

所以我們在宣告結果集,sql語句時,用StringBuilder。

因此:當需要進行頻繁修改字串的操作時先建立StringBuffer類物件進行操作,將最後結果轉化成String類物件返回,這樣效率會高很多。如: MySqlHelp.GetDataSet(connStr, CommandType.Text, sqlCmd.ToString();

StringBuffer(StringBuilder)其實可以看做“基本資料型別”String的包裝類(Wrapper),就像int與之對應的Integer等關係。

StringBuffer有快取的,如果你宣告一個字串只是接收傳過來的引數,然後進行業務邏輯處理,那麼假如你用很多個StringBuffer型別的物件,就比較浪費記憶體。這樣用String就更好。

2、 在字串拼接時,String 物件的速度並不會比 StringBuffer物件慢。

String 物件的字串拼接其實是被 JVM 解釋成了StringBuffer 物件的拼接,所以這些時候String 物件的速度並不會比StringBuffer 物件慢,而特別是以下的字串物件生成中, String 效率是遠要比 StringBuffer 快。

String S1 = “This is only a” + “ simple” + “ test”;

StringBuffer Sb = new StringBuilder(“This is only a”).append(“ simple”).append(“test”);

會發現,生成String S1 物件的速度簡直太快了,而這個時候 StringBuffer 居然速度上根本一點都不佔優勢。其實這是 JVM 的一個把戲,在 JVM 眼裡,這個

String S1 = “This is only a” + “ simple” + “test”;

其實就是:

String S1 = “This is only a simple test”;

所以當然不需要太多的時間了。但大家這裡要注意的是,如果你的字串是來自另外的 String 物件的話,速度就沒那麼快了,譬如:

String S2 = “This is only a”;

String S3 = “ simple”;

String S4 = “ test”;

String S1 = S2 +S3 + S4;

這時候 JVM 會規規矩矩的按照原來的方式去做

3、線上程安全方面不同

StringBuffer 字串變數(執行緒安全)

StringBuilder 字串變數(非執行緒安全)

       三者使用總結:在操作少量變動的資料時,使用String;在單執行緒中操作大量資料的字串時,使用StringBuilder;在多執行緒中操作大量資料的字串時,使用StringBuffer。

關於執行緒安全,非執行緒安全

       首先要明白執行緒的工作原理,jvm有一個main   memory(主儲存器),而每個執行緒有自己的working   memory(工作記憶),一個執行緒對一個variable(變數)進行操作時,都要在自己的working   memory裡面建立一個copy,操作完之後再寫入main   memory。多個執行緒同時操作同一個variable,就可能會出現不可預知的結果。根據上面的解釋,很容易想出相應的scenario。  而用synchronized(同步)的關鍵是建立一個monitor(監控模組),這個monitor可以是要修改的variable也可以其他你認為合適的object比如method,然後通過給這個monitor加鎖來實現執行緒安全,每個執行緒在獲得這個鎖之後,要執行完   load到workingmemory   ->   use&assign   ->   store到mainmemory   的過程,才會釋放它得到的鎖。這樣就實現了所謂的執行緒安全。 什麼是執行緒安全?執行緒安全是怎麼完成的(原理)? 

執行緒安全就是說多執行緒訪問同一程式碼,不會產生不確定的結果。編寫執行緒安全的程式碼是低依靠執行緒同步。

在介面方式中,執行緒有一個共享的資料成員,即: private   int   count   =10; 

而在繼承方式中,執行緒之間沒有共享的成員,而是各執行緒各自有一個私有成員,即: private   int   count   =10; 

執行緒安全一般都涉及到synchronized 就是一段程式碼同時只能有一個執行緒來操作 不然中間過程可能會產生不可預製的結果

如果你的程式碼所在的程序中有多個執行緒在同時執行,而這些執行緒可能會同時執行這段程式碼。如果每次執行結果和單執行緒執行的結果是一樣的,而且其他的變數的值也和預期的是一樣的,就是執行緒安全的。 舉例 比如一個 ArrayList 類,在新增一個元素的時候,它可能會有兩步來完成:1. 在 Items[Size] 的位置存放此元素;2. 增大 Size 的值。 在單執行緒執行的情況下,如果 Size = 0,新增一個元素後,此元素在位置 0,而且 Size=1; 而如果是在多執行緒情況下,比如有兩個執行緒,執行緒 A 先將元素存放在位置 0。但是此時 CPU 排程執行緒A暫停,執行緒 B 得到執行的機會。執行緒B也向此 ArrayList 新增元素,因為此時 Size 仍然等於 0 (注意哦,我們假設的是新增一個元素是要兩個步驟哦,而執行緒A僅僅完成了步驟1),所以執行緒B也將元素存放在位置0。然後執行緒A和執行緒B都繼續執行,都增加 Size 的值。 那好,現在我們來看看 ArrayList 的情況,元素實際上只有一個,存放在位置 0,而 Size 卻等於 2。這就是“執行緒不安全”了。