第八章 数组
一维数组
数组名称和指针是有区别的:数组是能确定大小的,而指针不行数组的地址是固定的,而指针不是
下标引用
(b + 3)//b地址偏移3个地址大小然后取值b + 3 先取值再加3b[-1] 这是合法的 就是向后一位2[array] 与 *(2 + (array)) 相等 所以与 array[2] 相等指针和下标很相似具体用哪个,因人而异,但是指针会比下标更有效率.
Int array[10],a;
for(a = 0;a < 10; a++){}
int *p;
p = array;
for(;p < array +10;p++){}
字符串复制
void strcpy(char *buffer,char const *string){while((*buffer++ = *string++) != '\0');}
声明const指针类型可以让编译器检查不能被修改的字符串有没有被修改
声明数组参数
int strlen(char *string);int strlen(char string[]);上述两种方式是对等的,但是方式一更为标准,这也就可以理解了为什么传递数组参数同样需要传递长度参数
初始化
不完全初始化
int vector[5] = {1,2,3};
自动计算数组长度
int vector[] = {1,2,3,4,5};
字符数组的初始化
char message[] = {'h','e','l','l','o','\0'};//此时的字符数组不是字符串常量(每个元素都有地址指向它)但是字符串常量就不一样了,它指向的是一坨内容。
多维数组
指向数组的指针:int number[10] ,*p = number;//合法的 p指向的是第一个元素int number[10][100],*p = number;//不合法 因为此时的number指向的是 int [100] ,而p只能指向int ,所以要用:int (*p)[100];
第九章 字符串、字符和字节
字符串基础
以NUL为结尾的的一串0个或者多个字符
字符串长度
strlen (char const * string);可以返回字符串长度if(strlen(x) >= strlen(y))...if((strlen(x) - strlen(y)) >= 0)...//这个判断永远为真因为两个类型都是无符号类型,当然如果强转int类型就行
不受限制的字符串函数
strcpy()//复制字符串 复制前最好检查长度是否满足strcat()//链接字符串 strcmp()//比较字符串strncpy()//注意的是结尾可能不是NUL结尾,所以最好将最后的字符设置为‘\0'strncat()strncmp()
字符串查找
查找一个字符串
· strchr
· strrchr
查找任何几个字符
strpbrk(string,"aeiou")在string中查找是否有 aeiou 顺序查找,返回第一次出现的位置
查找一个子串
strstr(char const *s1,char const *s2)查找子字符串,如果想实现strrstr(),则循环找找到最后一次即可
高级字符串查找
strspn(字符串1,字符数组)查找字符串1中,第一个在字符数组中不存在的位置strcspn(字符串1,字符数组)与上述相反,查找第一个符合条件的位置
查找标记
strtok(char *str,char const *sep)生成分隔符,NULL
错误信息
char * strerror(int error_number)返回一个指向描述错误的字符串的指针
字符串操作
字符分类
iscntrl任何控制字符isspace空白字符isdigit十进制数isxdigit十六进制数islower小写isupper大写isalpha字母isalnum字母加数字ispunct标点符号isgraph图形符号isprint可打印字符
字符转换
tolowertoupper
内存操作
如果遇到一些含NUL字符的字符串,又要处理复制之类的操作则:memcpymemmove //地址可重叠memcmpmemchrmemset
第十章 结构和联合体
结构基础知识
聚合数据类型
struct {...}x;
没有标签,直接创建了一个X结构体
struct SIMPLE{...};
创建了标签
结构体成员的访问
直接访问:a.p;间接访问:a->p;(a是个结构体指针)警惕陷阱:typedef struct {int a;SELF_REF3 *b;int c;}SELF_REF3;此时名称是在后面才被声明的,这样不行,解决方案:typedef struct SELF_REF3_TAG{int a;SELF_REF3_TAG *b;int c;}SELF_REF3;
不完整的声明
当两个结构体需要互相依赖的时候,则:
struct B;
struct A {struct B *partner;};
struct B {struct A *partner;}
这样即可
结构体的成员存储分配
struct ALIGN{char a;int b;char c;};struct ALIGN2{int b;char a;char c;};此时的两种结构体的占用内存大小是不同的
位段
struct CHA{unsigned ch : 7;unsigned font:6;unsigned siz:19;}struct CHA ch1;
案例:
struct DISK_FOR{unsigned command :5;unsigned sector:5;...};
#define DISK_FOR_SIG \((DISK_FOR *)0xc0200142)DISK_FOR_SIG ->command = 12;
...
联合体
联合体的所有成员引用的是内存中的相同位置。
struct VARIABLE{enum {INT,FLOAT,STRING} type;union {int i;float f;char *s;}value;};
通过type去访问类型