指針的各種名字,換個馬甲也得認識你啊。。
char * const p; //常量指針,p的值不可以修改
char const * p;//指向常量的指針,指向的常量值不可以改
const char *p; //和char const *p
int *p[n];-----指針數組,每個元素均爲指向整型數據的指針。
int (*p)[n];------p爲指向一維數組的指針,這個一維數組有n個整型數據。
int *p();----------函數帶回指針,指針指向返回的值。
int (*p)();------p爲指向函數的指針。
memcpy和strcpy:
memcpy用來做內存拷貝,你可以拿它拷貝任何數據類型的對象,可以指定拷貝的數據長度
strcpy就只能拷貝字符串了,它遇到'\0'就結束拷貝
extern char *strcpy(char *dest,char *src)
{ ASSERT((dest!=NULL)&&(src!=NULL));
Char *address = dest;
While((*dest++=*src++)!=’\0’)
Continue;
Return dest; }
extern void *memcpy(void *dest, void *src, unsigned int count);
{ ASSERT((dest!=NULL)&&(src!=NULL));
ASSERT((dest>src+count)||(src>dest+count));//防止內存重疊,也可以用restrict修飾指針
Byte* bdest = (Byte*)dest;
Byte* bsrc = (Byte*) src;
While(count-->0)
*bdest++ = **bsrc++;
Return dest; }
ASSERT():
這個宏通常原來判斷程序中是否出現了明顯非法的數據,如果出現了終止程序以免導致嚴重後果,同時也便於查找錯誤。
神馬時候分配神馬變量,有個sense比較好:
全局變量在main函數調用後,就開始分配,
靜態變量則是在main函數前就已經初始化了。
局部變量則是在用戶棧中動態分配的
char s1[]=‛aaaaaaaaaaaaaaa‛;
char *s2=‛bbbbbbbbbbbbbbbbb‛;
aaaaaaaaaaa是在運行時刻賦值的; 而bbbbbbbbbbb是在編譯時就確定的;
a=c[1]; //c是數組
a=p[1]; //p是指針
第一種在讀取時直接就把字符串中的元素讀到寄存器cl中,而第二種則要先把指針值讀到edx中,在根據edx讀取字符,顯然慢了。
在數組作爲形參的時候,只作爲地址處理:
Void Func(char a[100])
=>Sizeof(a) = 4
預編譯
預編譯又稱爲預處理,是做些代碼文本的替換工作。處理#開頭的指令,比如拷貝#include包含的文件代碼,#define宏定義的替換,條件編譯等,就是爲編譯做的預備工作的階段,主要處理#開始的預編譯指令,預編譯指令指示了在程序正式編譯前就由編譯器進行的操作,可以放在程序中的任何位臵。 c編譯系統在對程序進行通常的編譯之前,先進行預處理。
c提供的預處理功能主要有以下三種:1)宏定義 2)文件包含 3)條件編譯
const VS #define
請說出const與#define 相比,有何優點?
答:Const作用:定義常量、修飾函數參數、修飾函數返回值三個作用。被Const修飾的東西都受到強制保護,可以預防意外的變動,能提高程序的健壯性。 1) const 常量有數據類型,而宏常量沒有數據類型。編譯器可以對前者進行類型安全檢查。而對後者只進行字符替換,沒有類型安全檢查,並且在字符替換可能會產生意料不到的錯誤。 2) 有些集成化的調試工具可以對const 常量進行調試,但是不能對宏常量進行調試。
用宏定義交換兩個數:
a = a + b;
b = a - b;
a = a - b;
#define SWAP(a,b)\
(a)=(a)+(b);\
(b)=(a)-(b);\
(a)=(a)-(b);