学习笔记—C语言基础篇07

来源:互联网 发布:windows rm 命令 编辑:程序博客网 时间:2024/06/09 20:14
作用域:
局部变量:在函数内部定义的变量称为局部变量(auto),作用域为局部变量创建到函数结束;
全局变量:在函数外部定义的变量,作用于整个程序;
如果在代码中全局变量与局部变量有相同变量名,局部变量覆盖全局变量;
static:如果没初始化默认设置的值为0
静态局部变量:程序创建之初定义,只能在程序创建时被初始化一次,作用域 为函数内部;
静态全局变量:程序创建之初定义,只能在程序创建时被初始化一次,作用域缩小为只在本文件有效;
全局函数:在程序中声明的函数默认为全局函数,作用于整个项目;
静态函数:加static修饰,作用域缩小为只在本文件有效,如果和全局函数重名那么在该文件中使用static修饰的函数;
内存布局
内存可执行程序四区模型

代码区:
存放计算机程序指令
只读,共享

数据区:
1.字符串常量 char* s = "hello";
2.初始化数据区:
全局变量,全局常量,static修饰的全局,局部变量
3.未初始化数据区:(bss段)
全局变量,全局常量,static修饰的全局,局部变量
栈区:
在程序加载到内存中,系统自动分配给每个程序一定的空间(一般情况windos下一般为1-8M,linux下一般为1-16M)用来存储数据,当程序执行完成,系统自动回收
存放:局部变量,const修饰的常量(必须是局部变量),指针,结构体,联合体,枚举,函数的形参
堆区:
由程序员自己分配和释放的空间。
堆空间开辟
malloc / calloc / realloc
释放
free
内存模型
                                                                    合称数据区
代码区data区bss区 
堆区
栈区
开辟二级指针空间
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>#include <stdlib.h>int main(){      //先开辟外层空间存储一级指针      int **p = (int**)malloc(sizeof(int*)* 3);      for(int i = 0; i < 3;i++)      {            //开辟一级指针存变量地址            p[i] = (int*)malloc(sizeof(int*)*3);      }      for(int i = 0; i < 3;i++)      {            int sum = 0;            for(int j = 0; j < 3; j++)            {                  scanf("%d",&p[i][j]);                  sum += p[i][j];            }            printf("总成绩 %d\n",sum);      }//释放内存空间      for(int i = 0; i < 3;i++)      {            free(p[i]);//先释放内层            p[i] = NULL;      }      free(p);//再释放外层      p = NULL;      system("pause");      return 0;}
memset
#include<string.h>
void*memset(void*s地址,intc, size_tn);
功能:将s的内存区域的前n个字节以参数c填入
参数:
       s:需要操作内存s的首地址
       c:填充的字符,c虽然参数为int,但必须是unsigned char , 范围为0~255
       n:指定需要设置的大小
返回值:s的首地址
strcpy(操作的字符串
#include<string.h>
char*strcpy(char*dest,constchar *src);
功能:把src所指向的字符串复制到dest所指向的空间中,'\0'也会拷贝过
参数:
       dest:目的字符串首地址
       src:源字符首地址
返回值:
       成功:返回dest字符串的首地址
       失败:NULL
注意:如果参数dest所指的内存空间不够大,可能会造成缓冲溢出的错误
strncpy
#include<string.h>
char*strncpy(char*dest,constchar *src,size_tn);
功能:把src指向字符串的前n个字符复制到dest所指向的空间中,是否拷贝结束符看指定的长度是否包含'\0'
参数:
       dest:目的字符串首地址
       src:源字符首地址
       n:指定需要拷贝字符串个数
返回值:
       成功:返回dest字符串的首地址
       失败:NULL
memcpy(操作的一块内存空间以字节为单位
#include<string.h>
void*memcpy(void*dest,constvoid *src,size_tn);
功能:拷贝src所指的内存内容的前n个字节到dest所指的内存地址上。
参数:
       dest:目的内存首地址
       src:源内存首地址,注意:dest和src所指的内存空间不可重叠
       n:需要拷贝的字节数
返回值:dest的首地址
注意:当拷贝源和目标发生冲突时会可能会拷贝失败
memmove:相比memcpy更安全
memmove()功能用法和memcpy()一样,区别在于:dest和src所指的内存空间重叠时,memmove()仍然能处理,不过执行效率比memcpy()低些(如果dest和src 内存有冲突memmove会去开辟一个临时的空间,存储src所指的内存空间 的内容)。

memcmp
#include<string.h>
intmemcmp(constvoid*s1,constvoid *s2,size_tn);
功能:比较s1和s2所指向内存区域的前n个字节
参数:                                                        返回值:
       s1:内存首地址1                                相等:=0
       s2:内存首地址2                                大于:>0
       n:需比较的前n个字节                      小于:<0

开辟堆空间易错点
char* s = NULL;
s = (char*)malloc(sizeof(char)*10);//堆区
s = "hello";//此时s被修改到了字符串常量区了
printf("%p",s);
free(s);//此时找不到s的地址,会报错

开辟堆空间大小易错点
1、
int main()
{
     int* p = (int*)malloc(0);//开辟0个空间大小 程序不会报错 但是个野指针
     *P = 100;//操作野指针 可能会报错
     free(p);
}

2、
int main()
{
     int* p = (int*)malloc(2);//申请2个字节
     *P = 100;//操作4个字节
     free(p);//操作额外空间会出错
}
0 0
原创粉丝点击