C
备注
本节讲述 C 语言部分内容。施行标准为 C99
Const
const 是在编译阶段实现的,并且只对被const限定的变量进行检查。这意味着你可以另外设置一个指针来绕过限制
表达式短路
例如:
对于
表达式1&&表达式2若 计算出表达式 1 为 0 ,则无需对表达式 2 求值,表达式 2 被短路对于
表达式1||表达式2若 计算出表达式 1 非 0 ,则表达式 2 被短路
空指针
对一个NULL指针解引用是一个违法的操作。会直接无法通过编译
查找文件
C查找文件需要:头文件 direct.h 、 io.h 结构体 struct _finddata_t 和函数 _findfirst 、 _findnext 、 _fineclose 。
结构体 struct _finddata_t 被包含在头文件 io.h 中,其储存了文件的各种信息,完整定义如下:
struct _finddata_t{
unsigned attrib; //文件属性的储存位置
time_t time_create; //文件被创建时间
time_t time_access; //文件最后一次被访问的时间
time_t time_write; //文件最后一次被修改时间
_fsize_t size; //文件大小(字节)
char name[_MAX_FNAME]; //文件名
}
unsigned attrib:文件属性的储存位置。文件属性使用位来表示,包括:_A_ARCH(存档)、 _A_HIDDEN(隐藏)、_A_NORMAL(正常)、_A_RDONLY(只读)、_A_SUBDIR(文件夹)、_A_SYSTEM(系统)。
这些都是定义在头文件中的宏,可以直接被使用。多个属性之间通过异或组合。
_findfirst
函数 long _findfirst( char *filespec, struct _finddata_t *fileinfo );
函数的第一个参数用来指定文件名(允许通配符),第二个参数是一个用来存储信息的结构体,当查找失败时,返回0。查找成功时,返回一个可用于_findnext函数的文件句柄。
_findnext
函数**int _findnext( long handle, struct _finddata_t fileinfo );*
第一个参数就是_findfirst返回的long型句柄。当查找成功时,返回值为0,否则返回-1;
_findclose
函数**int _findclose(long handle);**用来结束查找。
示例:
#include<stdio.h>
#include <direct.h>
int main(void){
long hFIle;
struct _finddata_t fileinfo;
if((hFIle=_findfirst("*.*",&fileinfo))!=-1L)
{
do{
if (!(fileinfo.attrib & _A_SUBDIR))
printf("文件名:%-30s"
"文件大小:%-15d"
"字节\n"
,fileinfo.name
,fileinfo.size);
}while (_findnext(hFIle,&fileinfo)==0);
_findclose(hFIle);
}
return 0;
}
输出结果如下:
C::\Users\Dragon\CLionProjects\Test\_For_C11\cmake-build-debug\Test\_For_C11.exe
文件名:CMakeCache.txt 文件大小:21225 字节
文件名:cmake_install.cmake 文件大小:1483 字节 文件名:Makefile
文件大小:5290 字节 文件名:Test_For_C11.cbp 文件大小:5975 字节
文件名:Test_For_C11.exe 文件大小:43262 字节
Process finished with exit code 0
目录操作
头文件: sdtlib.h
#include <direct.h> //_getcwd(), _chdir()
#include <io.h> //_finddata_t, _findfirst(), _findnext(), _findclose()
#include <stdio.h>
#include <stdlib.h> //_MAX_PATH, system()
void main(void) {
char buffer[_MAX_PATH];
//获取当前工作目录
if (_getcwd(buffer, _MAX_PATH) == NULL)
perror("_getcwd error");
else
printf("%s\n", buffer);
//更改当前工作目录 - 相对路径方式
if (_chdir("./temp"))
printf("Unable to locate the directory you specified \n");
else
{
_getcwd(buffer, _MAX_PATH); //重新获取当前工作目录
printf("The CWD is: %s\n", buffer); //输出当前工作目录
system("type hello.c"); // system用于执行命令行指令
}
//更改当前工作目录 - 绝对路径方式
if (_chdir("F:\\temp")) //双反斜杠处理转义字符'\'
printf("Unable to locate the directory you specified \n");
else
{
_getcwd(buffer, _MAX_PATH);
printf("\n\nThe CWD is: %s\n", buffer);
system("dir *.*");
}
//查找当前目录中符合要求的文件, 并输出文件的相关信息
long hFile;
_finddata_t fileinfo;
if ((hFile = _findfirst("*.c", &fileinfo)) != -1L)
{
do
{
if (!(fileinfo.attrib & _A_SUBDIR)) //检查是不是目录, 如果不是,则进行处理
{
printf("%s, %ul bytes\n", fileinfo.name, fileinfo.size);
}
} while (_findnext(hFile, &fileinfo) == 0);
_findclose(hFile);
}
}
删除文件
头文件要求: stdio.h
函数原型: int remove(const char * filename);
可变参数 [#parm]
有时,您可能会碰到这样的情况,您希望函数带有可变数量的参数,而不是预定义数量的参数。C 语言为这种情况提供了一个解决方案,它允许您定义一个函数,能根据具体的需求接受可变数量的参数。下面的实例演示了这种函数的定义。
int func(int, ... ){
.
.
.
}
int main()
{
func(2, 2, 3);
func(3, 2, 3, 4);
}
请注意,函数 func() 最后一个参数写成省略号,即三个点号( … ),省略号之前的那个参数是 int ,代表了要传递的可变参数的总数。为了使用这个功能,您需要包含 stdarg.h ,该文件提供了实现可变参数功能的函数和宏。具体步骤如下:
定义一个函数,最后一个参数为省略号,省略号前面可以设置自定义参数。
在函数定义中创建一个 va_list 类型变量,该类型是在 stdarg.h 头文件中定义的。
使用 int 参数和 va_start 宏来初始化 va_list 变量为一个参数列表。宏 va_start 是在 stdarg.h 头文件中定义的。
使用 va_arg 宏和 va_list 变量来访问参数列表中的每个项。
使用宏 va_end 来清理赋予 va_list 变量的内存。
现在让我们按照上面的步骤,来编写一个带有可变数量参数的函数,并返回它们的平均值:
#include <stdio.h>
#include <stdarg.h>
double average(int num,...){
va_list valist;
double sum = 0.0;
int i;
// 为 num 个参数初始化 valist
va_start(valist, num);
// 访问所有赋给 valist 的参数
for (i = 0; i < num; i++)
{
sum += va_arg(valist, int);
}
// 清理为 valist 保留的内存
va_end(valist);
return sum/num;
}
int main(){
printf("Average of 2, 3, 4, 5 = %f\n", average(4, 2,3,4,5));
printf("Average of 5, 10, 15 = %f\n", average(3, 5,10,15));
}
当上面的代码被编译和执行时,它会产生下列结果。应该指出的是,函数 average() 被调用两次,每次第一个参数都是表示被传的可变参数的总数。省略号被用来传递可变数量的参数。
输出结果为:
Average of 2, 3, 4, 5 = 3.500000 Average of 5, 10, 15 = 10.000000
- 1