C++自修入門實境秀、C++ Primer 5版研讀秀 20/ ~頁127 Subscripting a Multidimensional Ar...
2:30
3.5.4. C-Style Character Strings C式的字元字串
→一種C風格的字串處理方式
C-style strings are not a type. Instead, they are a convention for how to represent and use character strings. 3:1:00
convention就是Style的由來,有怎樣的習慣和風格,自然就有怎樣的stype(型)了。
C Library String Functions
12:05
22:00一定要是最後一個元素為null(null terminated)的陣列,其指標(調用陣列時其實是調用其第一元素的指標)才能代入至表3.8的函式作引數
表3.8
strcmp(p1, p2) 39:00
Comparing Strings
31:20
string有兩種:
1.程式庫型別的string(library string)
2.C-Style string(西式字串、西型字串)
頁123
34:30
37:20指標的比較一定是指向(定址)相同的物件,才有意義
Caller Is Responsible for Size of a Destination String
1:1:30 呼叫者負責目的字串的大小
這都太不夠中文化的翻譯→
最後的結果必須是容得下字串運算結果的變數
1:6:00
The array we pass must be large enough to hold the generated string, including the null character at the end.
42:40
目的字串的大小是多少是由呼叫者來負責的
46:00
將兩個指標相加是無效(不對的illegal)且沒有意義的。
Instead we can use strcat and strcpy.
51:00
instead可以翻成中文的「那」
(非要這麼做不可的話)那我們可以
55:30
The code we show here, although a common usage pattern, is fraught with potential for serious error:
雖然我們這裡顯示的程式是常見的模式,但這樣的程式用起來依然是讓人步步驚心←
我們在此展示的程式碼,雖然是一種常見的使用模式,但滿載了導致嚴重錯誤的可能性:
仍是處處都是(佈滿了)陷阱
仍是處處是地雷
1:9:55
1:28:00 自訂取得陣列大小的兩種函式:
size_t sizeofanArrayEnd_Beg() {//用程式庫的 begin 和 end來算陣列的size
int arr[]{ 0,11,2,3,4,15 };
return end(arr) - begin(arr);
}
size_t sizeofanArray_sizeof() { //用 sizeof來計算
int arr[]{ 0,11,2,3,4,15 };
return sizeof(arr) / sizeof(*arr);
}
1:33:00
Unfortunately,programs similar to this code are widely distributed. Programs with such code are error-prone and often lead to serious security leaks.
遺憾的是,類似這裡程式碼的程式廣為散布。帶有這種程式碼的程式很容易出錯,而經常也會導致嚴重的安全洩漏問題。→
很不幸的,像這樣的程式碼幾乎可以說是觸處皆是,然而這樣的程式碼卻很容易造成致命的錯誤,甚至往往是資安漏洞的根源。
用library string 比用 C-Style string更安全也更有效率(性能也更好)
頁124
1:43:10
練習3.37
1:58:30
const char ca[] = { 'h','e','l','l','o' };
const char* cp = ca;
while (*cp) {
cout << *cp << endl;
++cp;
}
會陷入無窮迴圈。除非在記憶體中碰到使*cp=false(即*cp='\0';'\0'即null)才會出迴圈
練習3.38
2:10:20
練習3.39
bool compareStrEqual(string str,string str1) {
if (str==str1)
{
return true;
}
else
{
return false;
}
}
以下就已經是C-Style了。就是把字串表示成字元來運算,對待字串,就好像處理字元陣列一樣,所以離不開指標pointer。
bool compareStrEqual() {
char cstr[]("天下為公");
char cstr1[] ("天0下為公");
char* p = cstr;
char* p1 = cstr1;
while (p<end(cstr))
{
if (*p!=*p1)
{
return false;
}
else
{
++p;
++p1;
}
}
return true;
}
bool compareStrEqual() {
char cstr[]("天下為公");
char cstr1[] ("天下為公");
if (strcmp(cstr,cstr1)!=0)
{
return false;
}
else
{
return true;
}
}
上列字串字面值(string literal)初始化的陣列的會自動帶上null terminated作為被初始化陣列的最後元素;但是如下若用串列初始化(list initialization)則一定要記得自己手動加上null為最末元素才行。
bool compareStrEqual() {
char cstr[]{'1','2','3','\0'};
char cstr1[]{ '1','2','3','\0' };
if (strcmp(cstr,cstr1)!=0)
{
return false;
}
else
{
return true;
}
}
練習3.40
3:2:12
string compareStrEqual() {
char cstr[]{"曾經滄海難為水"};
char cstr1[]{"除卻巫山不是雲"};//當用字串字面值(string literal)初始化一個字元陣列,就自動幫我們補上最後一個元素null了
constexpr unsigned sz = sizeof(cstr) / sizeof(*cstr) +
sizeof(cstr1) / sizeof(*cstr1) + 1;//確實可以藉由constexpr來定義一個由運算式(變數)運算出來的值成為常值
char cstr2[sz];
strcpy_s(cstr2, cstr);//在Visual Studio的環境下,不允許用不帶「_s」的函式,除非要用一些特定的表述法(暫未瞭)
strcat_s(cstr2, ",");
strcat_s(cstr2, cstr1);
string str{ cstr2 };//只要是字元陣列(character arrays)就可以直接轉換成字串(字元字串)
return str;//str="曾經滄海難為水,除卻巫山不是雲"
}
3.5.5. Interfacing to Older Code
銜接舊的C++程式碼
Mixing Library string s and C-Style Strings
3:43:20
3:47:00 字串字面值(string literal)與string是不同型別的東西,因為字串字面值(string literal)就是一個帶有null-terminated的字元陣列(character arrays)
字串字面值(string literal)看起來像是一個字串,其實就是一個帶有null-terminated的字元陣列(character arrays),就好像我們說在指名/具名操作一個陣列時,其實是在操作該陣列第一個元素的指標
3:56:00 string下的c_str成員函式
是用來把字串string轉成帶有null結尾的字元陣列(character arrays)
c_str的意思是傳回一個C-styel character string。
頁125
4:8:30
4:12:00 只要string值改變,其c_str成員函式產生的字元陣列(character arrays)當然也會隨之失效了。
4:16:00
WARNING
If a program needs continuing access to the contents of the array returned by str(), the program must copy the array returned by c_str.
Using an Array to Initialize a vector
4:19:00
我們也沒辦法用一個vector去初始化一個陣列
Advice: Use Library Types Instead of Arrays
最好是用程式庫型別取代陣列
3.6. Multidimensional Arrays
4:41:50 4:43:00
嚴格說來,C++並沒有所謂的多維陣列
陣列的陣列(陣列所構成的陣列,5:12:00即陣列的元素是陣列)就是多維陣列
頁126
4:46:33
練習3.41
string compareStrEqual() {
int iarr[]{1,2,3,4,5,6};
vector<int>ivec(begin(iarr),end(iarr));//用陣列將vector初始化
vector<int>ivec1(begin(iarr) + 1, iarr + 5);//不必取用整個陣列大小
return "";
}
練習3.42
vector<int>ivec{2,3,4,5,6,7};
int iarr[6];
int* p = iarr;
for (vector<int>::iterator i = begin(ivec); i != end(ivec); ++i)
{
*p = *i; ++p;
}
for (auto i : iarr)
{
cout<<i<<" ";
}
cout << endl;
5:11:10
5:20:20
There is no limit on how many subscripts are used.
定義中的[]仍是叫下標(subscript)
That is, we can have an array whose elements are arrays of elements that are arrays, and so on.
也就是說,我們可已有一個陣列其元素是陣列,而該陣列的元素也是 陣列,依此類推。
也就是說,我們可以有一個陣列其元素是陣列,而該陣列的元素也是陣列,依此類推。
Initializing the Elements of a Multidimensional Array
頁127
5:33:40
Subscripting a Multidimensional Array
5:38:10
留言