C/C++哪些地方會用到pointer呢?

(原創) C/C++哪些地方會用到pointer呢? (C/C++) (C)

Abstract
學習C/C++,大家最大的障礙就是pointer,本文試著將pointer做整體的討論。

Introduction
C很多地方都用到pointer,C++則有不少替代方案,以下是C和C++會用到pointer的地方。

CC++
1.Pass by AddressReference
2.Pass Array to FunctionVector
3.char *std::string
4.Dynamic Allocation
(malloc(),linked list)
STL container
5.Function PointerFunction Object
6.N/AIterator
7.N/APolymorphism
8.N/APolymorphism object in container

1.Pass by Address
C語言

為了達成pass by address,C利用pointer達到此需求。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : pointer_swap.cpp
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use pointer to implement pass by address
7   Release     : 02/25/2007 1.0
8   */
9   #include < stdio.h >
10   #include < conio.h >
11  
12   void swap( int   * x, int   * y) {
13     int tmp =   * y;
14     * y =   * x;
15     * x = tmp;
16   }
17  
18   int main() {
19     int x =   1 ;
20     int y =   2 ;
21  
22     printf( " x=%d, y=%d/n " , x, y);
23     swap( & x, & y);
24     printf( " x=%d, y=%d/n " , x, y);
25   }


執行結果

x = 1 y = 2
x
= 2 y = 1


C++
C++提出了reference達成pass by address,使程式可讀性更高。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : reference_swap.cpp
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use reference to implement pass by address
7   Release     : 02/25/2007 1.0
8   */
9   #include < iostream >
10  
11   using   namespace std;
12  
13   void swap( int   & x, int   & y) {
14     int tmp = y;
15     y = x;
16     x = tmp;
17   }
18  
19   int main() {
20     int x =   1 ;
21     int y =   2 ;
22  
23     cout <<   " x= "   << x <<   " y= "   << y << endl;
24     swap(x,y);
25     cout <<   " x= "   << x <<   " y= "   << y << endl;
26   }

 

執行結果

x = 1 y = 2
x
= 2 y = 1


執行結果一樣,功能也一樣,皆是pass by address,C++的reference是不是更簡潔呢?

See Also
(原創) pointer和reference有什么差别呢? (C/C++)

2.Pass Array to Function
C語言

將陣列傳到function時,由於陣列可能很大,若用pass by value的方式傳進function,勢必造成大量copy的動作而降低效能,C語言是靠pointer的方式,將陣列第一個元素的位址以pointer的方式傳進function。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : ArrayPassToFunctionCStyle.c
5   Compiler    : Visual C++ 8.0 / ISO C++
6   Description : Demo how to use pass array to function by C Style
7   Release     : 01/03/2007 1.0
8   */
9   #include < stdio.h >
10  
11   void func( int   * start, size_t size) {
12     int   * end = start + size;
13    
14     while (start != end)
15       printf( " %d/n " , * start ++ );
16   }
17  
18   int main() {
19     int ia[] = { 0 , 1 , 2 };
20     func(ia, 3 );
21   }

 

執行結果

0
1
2


C++
array本身有很多缺點,C++建議用STL的vector取代array。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : VectorPassToFunction.cpp
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use pass vector to function
7   Release     : 02/26/2007 1.0
8   */
9   #include < iostream >
10   #include < vector >
11  
12   using   namespace std;
13  
14   void func(vector < int >   const   & ivec) {
15     vector < int > ::const_iterator iter = ivec.begin();
16     for (;iter != ivec.end() ; ++ iter) {
17       cout <<   * iter << endl;
18     }
19   }
20  
21   int main() {
22     int ia[] = { 0 , 1 , 2 };
23     vector < int > ivec(ia, ia +   sizeof (ia) /   sizeof ( int ));
24     func(ivec);
25   }


21行和22行

int ia[] =   { 0 , 1 , 2 } ;
vector
< int > ivec(ia, ia +   sizeof (ia) /   sizeof ( int ));


只是個便宜行事的寫法,因為vector本身並沒有如boost::array提供initializer,所以借用了array的initializer,再由array轉vector。實務上是用pushback()將資料塞進vector。

重點應該放在14行

void func(vector < int >   const   & ivec) {


只需傳vector型態即可,不須用pointer,也不需傳size。

vector還有很多優點,如靜態動態一次搞定,不像array還分靜態array和動態array,array唯一的優點就是速度較快,若你的程式非常重視執行速度,則應該考慮使用array。

See Also
(原創) 如何将array转成std::vector? (使用vector.insert) (C++) (STL)
(原創) 如何将array转成std::vector? (使用constructor) (C++) (STL)
(原創) 如何動態建立一維陣列? (C/C++)
(原創) 如何動態建立二維陣列(多維陣列)? (C)
(原創) 如何動態建立二維陣列(多維陣列)? (C++)
(原創) 由一維陣列模擬二維陣列(多維陣列) (C/C++)

3.字串
C語言
C語言沒有字串型別,而是用char array來模擬字串,由於本質是array,所以可以用pointer來表示字串,也因如此,造成C語言在操作字串時含其他語言差異甚大。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : C_string.c
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use C-Style string
7   Release     : 08/12/2007 1.0
8   */
9   #include < stdio.h >
10   #include < string .h >
11  
12   int main() {
13     char s1[ 15 ] =   " Hello " ;
14     char s2[] =   " World " ;
15    
16     strcat(s1, s2);
17    
18     printf( " %s/n " ,s1);
19    
20     char   * s3 =   " Hello " ;
21     char   * s4 =   " Hello " ;
22    
23     if (strcmp(s3, s4))
24       puts( " s3 and s4 are not the same " );
25     else
26       puts( " s3 and s4 are the same " );
27   }


執行結果

執行結果
Hello World
s3 and s4 are the same


16行

strcat(s1, s2);


字串相加,並沒有如期他語言很直覺的用s1 = s1 + s2;而得用strcat(),且s1和s2都是pointer。

23行

if (strcmp(s3, s4))
  puts(
" s3 and s4 are not the same " );
else
  puts(
" s3 and s4 are the same " );


比較字串是否相同,也必須用strcmp()比較兩個pointer所指向的string是否相同才可比較,不可以用

if (s3 == s4)


因為s3和s4都是pointer,這樣是比較兩個pointer是否相同,而不是比較string是否相同,這和其他語言差異甚大,也和不符合一般人直覺。

C++
C++的STL提供了string,改進了C的char *,用法非常直覺。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : CPP_string.cpp
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use std::string
7   Release     : 08/12/2007 1.0
8   */
9   #include < iostream >
10   #include < string >
11  
12   using   namespace std;
13  
14   int main() {
15     string s1 =   " Hello " ;
16     string s2 =   " World " ;
17    
18     s1 = s1 + s2;
19    
20     cout << s1 << endl;
21    
22     string s3 =   " Hello " ;
23     string s4 =   " Hello " ;
24    
25     if (s3 == s4)
26       cout <<   " s3 and s4 are the same "   << endl;
27     else
28       cout <<   " s3 and s4 are not the same "   << endl;
29   }


執行結果

Hello World
s3 and s4 are the same


18行

s1 = s1 + s2;


字串相加,只要直覺的相加即可,符合大部分語言的習慣。

25行

if (s3 == s4)
  cout
<<   " s3 and s4 are the same "   << endl;
else
  cout
<<   " s3 and s4 are not the same "   << endl;


字串比較,也直接用==即可,簡單明瞭。

在C++,建議使用string,而且還可搭配強大的STL algorithm,功能強大且代碼乾淨易懂。

4.Dynamic Allocation
C語言
由於C語言是典型的靜態語言,使用array時必須事先定義好大小,這樣compiler才能做最佳化,若要讓C語言有動態功能,必須使用malloc()配合資料結構的linked list。

1   /*  
2   (C) OOMusou 2008 http://oomusou.cnblogs.com
3  
4   Filename    : DS_linked_list_simple.c
5   Compiler    : Visual C++ 8.0
6   Description : Demo how to use malloc for linked list
7   Release     : 03/22/2008 1.0
8   */
9   #include < stdio.h >
10   #include < stdlib.h >
11   #include < string .h >
12  
13   #define SLEN 255
14  
15   struct list {
16     int   no;
17     char name[SLEN];
18     struct list * next;
19   };
20  
21   int main() {
22     int no;
23     char s[ 255 ];
24    
25     struct list * head    = NULL;
26     struct list * current = NULL;
27     struct list * prev    = NULL;
28    
29     while ( 1 ) {
30       printf( " No. = " );
31       scanf( " %d " , & no);
32      
33       if (no ==   0 )
34         break ;
35    
36       printf( " Name = " );
37       scanf( " %s " , s);
38      
39       current = ( struct list * )malloc( sizeof ( struct list));
40       if (current == NULL)
41         exit(EXIT_FAILURE);
42        
43       current -> next = NULL;
44      
45       current -> no = no;
46       strncpy(current -> name, s, SLEN - 1 );
47       current -> name[SLEN - 1 ] =   ' /0 ' ;
48      
49       if (head == NULL)
50         head = current;
51       else
52         prev -> next = current;
53        
54       prev = current;
55     }
56    
57     // display linked list
58     current = head;
59     while (current != NULL) {
60       printf( " No. = %d, Name = %s/n " , current -> no, current -> name);
61       current = current -> next;
62     }
63    
64     // free linked list
65     current = head;
66     while (current != NULL) {
67       prev = current;
68       current = current -> next;
69       free(prev);
70     }
71   }


執行結果

No. =   1
Name
= clare
No.
=   2
Name
= jessie
No.
=   0
No.
=   1 , Name = clare
No.
=   2 , Name = jessie


39行

current = ( struct list * )malloc( sizeof ( struct list));


使用了malloc()動態新增linked list的node。

64行

// free linked list
current = head;
while (current != NULL) {
  prev
= current;
  current
= current -> next;
  free(prev);
}


由於malloc()使用了heap上的記憶體,必須手動使用free()將記憶體釋放,否則會造成memory leak。

C++
vector本身就可以動態擴張,而且又會自動釋放記憶體,因此可以取代linked list。

1   /*  
2   (C) OOMusou 2008 http://oomusou.cnblogs.com
3  
4   Filename    : DS_linked_list_simple_vector_class.cpp
5   Compiler    : Visual C++ 8.0
6   Description : Demo how to use vector instead of linked list
7   Release     : 03/22/2008 1.0
8   */
9   #include < iostream >
10   #include < string >
11   #include < vector >
12  
13   using   namespace std;
14  
15   class List {
16   public :
17     int no;
18     string name;
19   };
20  
21   int main() {
22     vector < List > vec;
23    
24     while ( 1 ) {
25       List list;
26       cout <<   " No. = " ;
27       cin >> list.no;
28      
29       if (list.no ==   0 )
30         break ;
31    
32       cout <<   " Name = " ;
33       cin >> list.name;
34      
35       vec.push_back(list);
36     }
37    
38     vector < List > ::iterator iter = vec.begin();
39     for (; iter != vec.end(); ++ iter)
40       cout <<   " No. = "   << iter -> no <<   " , Name = "   << iter -> name << endl;
41   }


執行結果

No. =   1
Name
= clare
No.
=   2
Name
= jessie
No.
=   0
No.
=   1 , Name = clare
No.
=   2 , Name = jessie


15行

class List {
public :
 
int no;
 
string name;
};


C++提供了class取代struct。

22行

vector < List > vec;


使用vector取代linked list。

35行

vec.push_back(list);


只需簡單的使用push_back()即可動態新增。

而且vector也不用管理記憶體,不會有memory leak的問題。

See Also
(原創) 簡單的Linked List實現 (C/C++) (Data Structure)  
(原創) 如何將輸入的字串存到記憶體後,再一起印出來? (C/C++)

5.Function Pointer
function pointer出自一個很簡單的需求:『該如何將function如變數一樣傳到另外一個function?』C語言使用function pointer來達成。

C語言

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : funtion_pointer.c
5   Compiler    : Visual C++ 8.0
6   Description : Demo how to use function pointer
7   Release     : 03/30/2008 1.0
8   */
9   #include < stdio.h >
10  
11   typedef int ( * predicate)( int );
12  
13   int is_odd( int i) {
14     return i %   2   ?   1 : 0 ;
15   }
16  
17   int is_even( int i) {
18     return i %   2   ?   0 : 1 ;
19   }
20  
21   void print_array( int   * beg, int   * end, predicate fn) {
22     do {
23       if (( * fn)( * beg))
24         printf( " %d " , * beg);
25     } while ( ++ beg != end);
26   }
27  
28   int main() {
29     int ia[] = { 1 , 2 , 3 };
30     int size =   sizeof (ia) /   sizeof ( int );
31    
32     printf( " Odd: " );
33     print_array(ia, ia + size, is_odd);
34     printf( " /n " );
35     printf( " Even: " );
36     print_array(ia, ia + size, is_even);
37   }


執行結果

Odd: 1   3
Even:
2  


11行

typedef int ( * predicate)( int );


利用typedef定義一個predicate型態的function pointer,傳入為int,傳出為int,雖然不一定得自行用typedef定義,但function pointer很容易寫成很複雜很難懂的程式,所以建議用typedef重新定義。

21行

void print_array( int   * beg, int   * end, predicate fn) {


宣告print_array最後一個參數為predicate這個function pointer型態,可傳入一個function pointer。

13行、17行

int is_odd( int i) {

 

int is_even( int i) {


為兩個符合predicate型態要求的function,因此日後可以傳入print_array()。

33行、36行

print_array(ia, ia + size, is_odd);

 

print_array(ia, ia + size, is_even);


使 用function pointer有什麼好處呢?在這兩行可以充分的看出,print_array()是不變的,若將來需求改變,如想印3的倍數,只要符合 predicate規格的function即可,在實務上,我們常利用function pointer來達成callback。

C++
C++提供了function object(functor)取代function pointer。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : funtion_object2.cpp
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use function object
7   Release     : 03/30/2008 1.0
8   */
9   #include < iostream >
10  
11   using   namespace std;
12  
13   template < typename T >
14   struct is_odd {
15     bool   operator () (T i) {
16       return i % 2 ?   true : false ;
17     }
18   };
19  
20   template < typename T >
21   struct is_even {
22     bool   operator () (T i) {
23       return i % 2 ?   false : true ;
24     }
25   };
26  
27   template < typename T, typename U >
28   void print_array(T beg, T end, U fn) {
29     do {
30       if (fn( * beg))
31         cout <<   * beg <<   "   " ;
32     } while ( ++ beg != end);
33   };
34  
35   int main() {
36     int ia[] = { 1 , 2 , 3 };
37    
38     cout <<   " Odd: " ;
39     print_array(ia, ia +   3 , is_odd < int > ());
40    
41     cout << endl;
42    
43     cout <<   " Even: " ;
44     print_array(ia, ia +   3 , is_even < int > ());
45   }


執行結果

Odd: 1   3
Even:
2  


13行

template < typename T >
struct is_odd {
 
bool   operator () (T i) {
   
return i % 2 ?   true : false ;
  }
};


是 一個典型的functor,基本上是靠對operator()作overloading而來,若配合constructor還能傳參數進來,由於都是 public,所以習慣上使用struct。不一定得使用template,只是functor也支援template就是了。

27行

template < typename T, typename U >
void print_array(T beg, T end, U fn) {
 
do {
   
if (fn( * beg))
      cout
<<   * beg <<   "   " ;
  }
while ( ++ beg != end);
};


寫法幾乎和C語言一樣,只不過多了template而已,但template可用可不用。

39行、44行

print_array(ia, ia +   3 , is_odd < int > ());

 

print_array(ia, ia +   3 , is_even < int > ());


也和C語言很類似。

function object的優點在於語法較高階,若配合constructor,則比function object更強,在(原創) Function Pointer、Delegate和Function Object (C/C++) (template) (C#) 有詳細的討論。

See Also
(原創) Function Pointer、Delegate和Function Object (C/C++) (template) (C#)
(原創) 如何使用Function Object? (C/C++) (STL)

接下來要談的,都是C++專屬的東西,在C沒有。一個基本的觀念:『C++的pointer最好只把它當成operator去看待,不要再用C的pointer是一個記憶體位址,指向一個變數』 的思維,也就是說,* 只是個符號,代表一些特定的意義,這樣會比較容易理解。

6.Iterator (C沒有)
C++ STL的iterator,是個操作很像poiner的smart pointer(請參考(原創) iterator到底是不是pointer? (C/C++) (STL) )。STL的container,就是利用iterator存取每個元素。

1   #include < vector >
2   #include < iostream >
3  
4   using   namespace std;
5  
6   int main() {
7     vector < int > ivec;
8     ivec.push_back( 1 );
9     ivec.push_back( 2 );
10     ivec.push_back( 3 );
11     ivec.push_back( 4 );
12    
13     for (vector < int > ::iterator iter = ivec.begin(); iter != ivec.end(); ++ iter)
14       cout <<   * iter << endl;
15   }


執行結果

1
2
3
4


iterator可以++、--、*、->,使用起來跟pointer一樣。

See Also
(原創) iterator到底是不是pointer? (C/C++) (STL)

7.Polymorphism (C沒有)
C++有三種物件表示方式:object, pointer, reference,C#只有object很單純,但對於最重要的多型,C++不能用object表示,這會造成object slicing,必須用pointer和reference達成。

1   /*  
2   (C) OOMusou 2007 http://oomusou.cnblogs.com
3  
4   Filename    : PolymorphismPointerReference.cpp
5   Compiler    : Visual C++ 8.0 / BCB 6.0 / gcc 3.4.2 / ISO C++
6   Description : Demo how to use pointer & reference for polymorphism
7   Release     : 03/20/2007 1.0
8   */
9   #include < iostream >
10   #include < string >
11  
12   using   namespace std;
13  
14   class Student {
15   public :
16     string name;
17    
18   protected :
19     Student() {}
20     Student( char   const * name) : name( string (name)) {}
21  
22   public :
23     virtual   string job() const   =   0 ;
24   };
25  
26   class Bachelor : public Student {
27   public :
28     Bachelor() {}
29     Bachelor( char   const * name) : Student(name) {}
30  
31   public :
32     string job() const {
33       return   " study " ;
34     }
35   };
36  
37   class Master : public Student {
38   public :
39     Master() {}
40     Master( char   const * name) : Student(name) {}
41    
42   public :
43     string job() const {
44       return   " study, research " ;
45     }
46   };
47  
48   int main() {
49     // C# : Student John = new Bachelor("John");
50     // use pointer
51     Student * John =   & Bachelor( " John " );
52     cout << John -> job() << endl;
53    
54     // use reference
55     Student & Jack = Bachelor( " Jack " );
56     cout << Jack.job() << endl;
57  
58     // C# : Student Mary = new Master("Mary"); 
59     Student * Mary =   & Master( " Mary " );
60     cout << Mary -> job() << endl;
61    
62     Master * Jeny;
63     Jeny =   new Master;
64     cout << Jeny -> job() << endl;
65   }


執行結果

study
study
study
, research


49行和58行為C#的寫法,使用object即可,但若用C++,51行為pointer寫法,55行為reference寫法,但不能使用object寫法。

See Also
(原創) 什麼是物件導向(Object Oriented)? (C/C++) (C#)


8.Polymorphism object in container (C沒有)
若要將多型的object放進container,則一定得用pointer,因為reference不能copy,這寫是C++與C#差異很大的地方。

繼續上一個多型的程式,現在我們想將這些多型的object放進vector內。

  1   /*  
  2   (C) OOMusou 2006 http://oomusou.cnblogs.com
  3  
  4   Filename    :Polymorphism.cpp
  5   Compiler    : Visual C++ 8.0 / ISO C++
  6   Description : Demo how to use Object Decomposition and Polymorphism.
  7   Release     : 01/12/2007 1.0
  8   */
  9   #include < iostream >
10   #include < vector >
11   #include < string >
12  
13   using   namespace std;
14  
15   class Student {
16   protected :
17     // constructor of abstract base class, since student
18     // can't be initiated, constructor just can be called
19     // by constructor of derived class, so put it in protected
20     // level.
21     Student( const   char * _name) : name( string (_name)) {}
22  
23   public :
24     string getName() const { return   this -> name; }
25     // pure virtual fuction
26     virtual   string job() const   =   0 ;
27  
28   private :
29     string name;
30   };
31  
32   // public inheritance
33   class Bachelor : public Student {
34   public :
35     // call constructor of abc myself.
36     Bachelor( const   char * name) : Student(name) {};
37  
38   public :
39     string job() const { return   " study " ; };
40   };
41  
42   class Master : public Student {
43   public :
44     Master( const   char * name) : Student(name) {};
45  
46   public :
47     string job() const { return   " study, research " ; };
48   };
49  
50   // new class for further
51   /*
52   class Doctor : public Student {
53   public:
54     Doctor(const char* name) : Student(name) {};
55  
56   public:
57     string job() const { return "study, research, teach"; };
58   };
59   */
60  
61   class Lab {
62   public :
63     // pass reference of student
64     void add(Student & );
65     void listAllJob() const ;
66  
67   private :
68     // put pointer of student in member vector, can't
69     // put reference in vector.
70     vector < Student *> member;
71   };
72  
73   void Lab::add(Student & student) {
74     // _student is reference of student object
75     // &_student is pointer of _student reference
76     this -> member.push_back( & student);
77   }
78  
79   void Lab::listAllJob() const {
80     // POWER of Polymorphism !!
81     // (*iter) automatically refer to derived object,
82     // this is called "dynamic binding".
83     // if you add new object in the future, you don't
84     // need to maintain this code.
85     for (vector < Student *> ::const_iterator iter =   this -> member.begin(); iter !=   this -> member.end(); ++ iter) {
86       cout << ( * iter) -> getName() <<   " 's job: "   << ( * iter) -> job() << endl;
87     }
88   }
89  
90   int main() {
91     Bachelor John( " John " );
92     Master   Mary( " Mary " );
93     // Doctor   Jack("Jack");
94  
95     Lab CSLab;
96     CSLab.add(John);
97     CSLab.add(Mary);
98     // CSLab.add(Jack);
99  
100     CSLab.listAllJob();
101   }


執行結果

John's job:study
Mary's job:study
, research


70行

private :
 
// put pointer of student in member vector, can't
 
// put reference in vector.
  vector < Student *> member;
};


member是一個要放多型物件的vector,這裡一定要用pointer,不能用reference。

79行

void Lab::add(Student & student) {
 
// _student is reference of student object
 
// &_student is pointer of _student reference
  this -> member.push_back( & student);
}


Student& student是reference,但&student是pointer,因為&在C++同時有兩個意義,要看使用位置而定。

79行

void Lab::listAllJob() const {
 
// POWER of Polymorphism !!
 
// (*iter) automatically refer to derived object,
 
// this is called "dynamic binding".
 
// if you add new object in the future, you don't
 
// need to maintain this code.
  for (vector < Student *> ::const_iterator iter =   this -> member.begin(); iter !=   this -> member.end(); ++ iter) {
    cout
<< ( * iter) -> getName() <<   " 's job: "   << ( * iter) -> job() << endl;
  }
}


由於*iter還是pointer,所以要括號後再用->,由於這是個多型的container,所以日後若有新的多型object,就再也不需要改code了,這就是多型的威力。

Conclusion
總算將全篇寫完了,也了了自己的心願,從頭到尾橫跨的時間超過一年,哈,主要是將自己學習C與C++關於pointer的心得做整理留下記錄

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值