梦开始的地方——C语言文件操作详解

news2024/9/21 16:37:01

文章目录

  • C语言文件操作
    • 1. 什么是文件?
    • 2.文件指针
    • 3.文件的打开和关闭
    • 4.文件的顺序读写
      • fgetc&fputc
      • fgets&fputs
      • fread&fwrite
      • fscanf&fprintf
      • scanf/fscanf/sscanf 对比 printf/fprintf/sprintf
    • 5.文件的随机读写(fseek&ftell &rewind)
    • 6. 文件结束判定
    • 7. 文件在存储形式
    • 8. 文件缓冲区


C语言文件操作

1. 什么是文件?

所谓的文件就是存储在计算机磁盘上的文件,在程序设计中,谈到文件一般可以分为两种文件。

  • 程序文件

    比如后缀为.c的C语言的源程序文件,还有.exe的可执行文件(在windows中)。不过在Linux系统中文件后缀名只是起到一个标识作用,后缀和文件类型无关。

  • 数据文件

    数据文件的内容不一定是程序,而是程序运行是读写的数据。比如程序运行时需要从中读取数据的文件,或者是程序输出内容的文件,比如.txt的文本文件。

而C语言文件操作一般围绕的就是数据文件,有的时候我们希望把一些数据保存到磁盘中永久存储,而不是在内存中,停止程序数据就丢失了。

2.文件指针

缓冲文件系统中,关键的概念就是”文件类型指针“,简称文件指针

每个被使用的文件都在内存中开辟了一个相应的文件信息区,用来存放文件的相关信息(比如文件的标识符,文件名,文件的当前位置等)。

比如下面就是devcpp中在stdio.h头文件中有以下声明:

  struct _iobuf {
    char *_ptr;//文件输入的下一个位置
    int _cnt;//当前缓冲区的相对位置
    char *_base;//文件的起始位置
    int _flag;//文件标标志
    int _file;//文件描述符id
    int _charbuf;//检查缓冲区状况,如果无缓存区则不读取
    int _bufsiz;//缓冲区大小
    char *_tmpfname;//临时文件名
  };
  typedef struct _iobuf FILE;

不同的编译器FILE类型可以会略有差异的,但是都差不太多。

每当C程序打开一个文件的时候,系统会根据文件的情况自动创建一个FILE结构的变量,并填充其中的信息,调用者不用关注其实现,只需要使用就好了。

使用FILE一般是通过指针来维护这个变量,使用起来更加方便。

FILE* pf;//文件指针变量

pf是一个指向FILE类型数据的指针变量,可以让pf指向某个文件的文件信息区域(一个结构体变量),通过该文件信息区中的信息就能狗访问该文件,也就是说通过文件指针变量能够找到与它关联的文件

在这里插入图片描述

3.文件的打开和关闭

文件在读写之前应该先打开文件,在使用结束之后应该关闭文件 。因为一个程序打开的文件数量是有限的。

C语言在打开文件的同时,都会返回一个FILE*的指针变量指向该文件,也相当于建立了指针和文件的关系。

C语言标准规定使用fopen函数来打开文件,fclose来关闭文件

FILE *fopen( const char *filename, const char *mode );
int fclose ( FILE * stream );
  • filename:文件路径
  • mode:文件打开方式
  • fopen打开文件失败返回空指针
文件使用方式含义如果指定文件不存在
“r”(只读)为了输入数据,打开一个已经存在的文本文件出错
“w”(只写)为了输出数据,打开一个文本文件自动建立一个新的文件
“a”(追加)向文本文件尾添加数据自动建立一个新的文件
“rb”(只读)为了输入数据,打开一个二进制文件出错
“wb”(只写)为了输出数据,打开一个二进制文件自动建立一个新的文件
“ab”(追加)向一个二进制文件尾添加数据自动建立一个新的文件
“r+”(读写)为了读和写,打开一个文本文件出错
“w+”(读写)为了读和写,建议一个新的文件自动建立一个新的文件
“a+”(读写)打开一个文件,在文件尾进行读写自动建立一个新的文件
“rb+”(读写)为了读和写打开一个二进制文件出错
“wb+”(读写)为了读和写,新建一个新的二进制文件自动建立一个新的文件
“ab+”(读写)打开一个二进制文件,在文件尾进行读和写自动建立一个新的文件

文件打开关闭实例

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main()
{
	FILE* pf = fopen("test.txt","w");
	if (pf == NULL)
	{
		printf("打开文件失败!\n%s", strerror(errno));
	}
    //关闭文件
	fclose(pf);
    pf = NULL;


	return 0;
}

4.文件的顺序读写

功能函数名适用于
字符输入函数fgetc所有输入流
字符输出函数fputc所有输出流
文本行输入函数fpusc所有输入流
文本行输出函数fgets所有输出流
格式化输入函数fscanf所有输入流
格式化输出函数fprintf所有输出流
二进制输入fread文件
二进制输出fwrite文件

C语言程序在运行起来的时候

会默认打开3个流

  • stdin:标准输入流(键盘)
  • stdout:标准输出流(屏幕)
  • stderr:标准错误流(屏幕)

是一个高度抽象的概念。举个例子::

我们写代码可能要操作硬盘或者U盘又或者是屏幕或者网卡,当我们要操作这么多外部设备的时候,需要要知道怎么用代码去操作它们,但每一种设备的操作方式就是不一样的,这样也是非常麻烦的,学习成本也比较高。于是这个概念就诞生了,我们可以把这些外部设备当作成流,我们写代码只需要关心怎怎么把数据写到流里面去,和怎么从流里面读取数据就够了,具体的流和操作系统的交互C语言已经帮我们封装好了,不需要我们去关心。

fgetc&fputc

  • fgetc:从文件中读取一个字符,读取错误或者读取到文件末尾返回EOF

  • gputc:写入一个字符到文件中,写入失败返回EOF

int fgetc( FILE *stream );
int fputc( int c, FILE *stream );

写入字符到文件中

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main()
{
	FILE* pf = fopen("test.txt", "w");//以写入的方式打开test.txt文件
	if (pf == NULL)
	{
		printf("打开文件失败!\n%s", strerror(errno));
	}
	else
	{
		int i = 0;
		for (i = 'a'; i <= 'z'; i++)
		{
			fputc(i, pf);//向文件里写入字符
		}
	}
	if (pf != NULL)
	{
		//关闭文件
		fclose(pf);
		pf = NULL;
	}


	return 0;
}

从文件中读取字符

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main()
{
	FILE* pf = fopen("test.txt", "r");//以只读的方式打开test.txt文件
	if (pf == NULL)
	{
		printf("打开文件失败!\n%s", strerror(errno));
	}
	else
	{
		int ch = 0;
		while ((ch = fgetc(pf)) != EOF)
		{
			printf("%c ", ch);
		}
	}
	if (pf != NULL)
	{
		//关闭文件
		fclose(pf);
		pf = NULL;
	}


	return 0;
}

fputc也可以从标准输出流中打印

#include <stdio.h>

int main()
{
	char ch = 'a';
	fputc(ch, stdout);//从标准输出流中打印
	return 0;
}

fgets&fputs

  • fgets:从文件中读取一行字符串,读取失败或者读取到文件末尾返回NULL
  • fputs:这些函数中的每一个都返回一个非负值。出现错误时,fputs返回EOF
char *fgets( char *string, int n, FILE *stream );
int fputs( const char *string, FILE *stream );

写入数据到文件中

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main()
{
	FILE* pf = fopen("test.txt", "w");//以写入的方式打开文件
	if (pf == NULL)
	{
		printf("文件打开失败!%s", strerror(errno));
	}
	else
	{
		fputs("第一行\n", pf);
		fputs("第二行\n", pf);
		fputs("第三行\n", pf);
	}
	//关闭文件
	if (pf != NULL)
	{
		fclose(pf);
		pf = NULL;
	}

	return 0;
}

从文件中读取一行

#include <stdio.h>
#include <string.h>
#include <errno.h>
int main()
{
	FILE* pf = fopen("test.txt", "r");//以只读的方式打开文件
	if (pf == NULL)
	{
		printf("文件打开失败!%s", strerror(errno));
	}
	else
	{
		char ch[10] = { 0 };
		fgets(ch, 11, pf);//读取第一行10个字节的数据到ch中
		printf("%s", ch);
	}
	//关闭文件
	if (pf != NULL)
	{
		fclose(pf);
		pf = NULL;
	}

	return 0;
}

也可以用while循环读取多行

char ch[10] = { 0 };
while (fgets(ch, 10, pf) != NULL)//一次读取9个字节
{
    printf("%s", ch);
}

也可以从标准输入中读取

#include <stdio.h>

int main()
{
	char ch[10] = { 0 };
	fgets(ch, 10, stdin);//从键盘中读取字符串到ch中
	printf("%s", ch);
	return 0;
}

通过标准输出打印到屏幕上

#include <stdio.h>

int main()
{
	char ch[10] = "hello";
	fputs(ch,stdout);
	
	return 0;
}

fread&fwrite

  • fwrite:fwrite返回实际写入的完整项目数,如果发生错误,该值可能小于count。此外,如果发生错误,则无法确定文件位置指示符。
  • fread:返回实际读取的完整项目数,如果发生错误或在到达count之前遇到文件结尾,则该值可能小于count。使用feof或ferror函数将读取错误与文件结束条件区分开来。如果大小或计数为0,fread返回0,缓冲区内容不变
size_t fwrite( const void *buffer, size_t size, size_t count, FILE *stream );

size_t fread( void *buffer, size_t size, size_t count, FILE *stream );
  • buffer:读取或者写入的数据的地址
  • size:单个数据的大小(字节)
  • count:数据的个数
  • stream:文件指针

写入代码实例

#include <stdio.h>
struct Stu
{
	char name[20];
	int age;
};
int main()
{
	FILE* pf = fopen("test.txt", "wb");//以二进制写文件方式打开
	if (pf == NULL)
	{
		printf("文件打开失败!\n");
	}
	else
	{
		//写入文件
		struct Stu s = { "张三",17 };
		fwrite(&s, sizeof(s), 1, pf);
	}
	


	//关闭文件
	if (pf != NULL)
	{
		fclose(pf);
		pf = NULL;
	}


	return 0;
}

读取代码实例

#include <stdio.h>
struct Stu
{
	char name[20];
	int age;
};
int main()
{
	FILE* pf = fopen("test.txt", "rb");//以二进制读文件方式打开
	if (pf == NULL)
	{
		printf("文件打开失败!\n");
	}
	else
	{
		//读文件
		struct Stu s = { 0 };
		fread(&s, sizeof(s), 1, pf);
		printf("%s %d", s.name, s.age);
	}
	


	//关闭文件
	if (pf != NULL)
	{
		fclose(pf);
		pf = NULL;
	}


	return 0;
}

fscanf&fprintf

fscanf和fprintf函数是用来格式化写入和格式化读取文件的函数

int fscanf( FILE *stream, const char *format [, argument ]... );
int fprintf( FILE *stream, const char *format [, argument ]...);

格式化写入数据到文件

#include <stdio.h>
struct Stu
{
	char name[20];
	int age;
};
int main()
{
	FILE* pf = fopen("test.txt", "w");//以写文件方式打开
	if (pf == NULL)
	{
		printf("文件打开失败!\n");
	}
	else
	{
		//格式化写入文件
		struct Stu s = { "张三",20};
		fprintf(pf, "%s %d", s.name, s.age);
		
	}
	


	//关闭文件
	if (pf != NULL)
	{
		fclose(pf);
		pf = NULL;
	}


	return 0;
}

格式化从文件中读取

#include <stdio.h>
struct Stu
{
	char name[20];
	int age;
};
int main()
{
	FILE* pf = fopen("test.txt", "r");//以读文件方式打开
	if (pf == NULL)
	{
		printf("文件打开失败!\n");
	}
	else
	{
		//格式化读取文件
		struct Stu s = { 0 };
		fscanf(pf, "%s %d", s.name, &(s.age));
		fprintf("%s %d\n",s.name,s.age);
		
	}
	


	//关闭文件
	if (pf != NULL)
	{
		fclose(pf);
		pf = NULL;
	}


	return 0;
}

他们俩也可以实现和printfscanf的效果

//格式化读取文件
		struct Stu s = { 0 };
		fscanf(stdin, "%s %d", s.name, &(s.age));
		fprintf(stdout,"%s %d\n", s.name, s.age);

scanf/fscanf/sscanf 对比 printf/fprintf/sprintf

前面两个一个介绍了,而sscanfsprintf是将格式化的数据和字符串互相转换

int sscanf( const char *buffer, const char *format [, argument ] ... );
int sprintf( char *buffer, const char *format [, argument] ... );
#include <stdio.h>
struct Stu
{
	char name[20];
	int age;
};
int main()
{
	struct Stu s1 = { "张三",20 };
	char ch[20] = { 0 };
	//sprintf可以把结构化的数据转换为一个字符串
	sprintf(ch, "%s %d", s1.name, s1.age);
	struct Stu s2 = { 0 };
	//sscanf可以把一个字符串转换为一个结构化的数据
	sscanf(ch, "%s %d", s2.name, &(s2.age));
	printf("%s %d\n", s2.name, s2.age);


	return 0;
}

它们几个又什么区别呢?

  • scanf&printf:是应用于标准输入流和输出流的格式化输入输出语句
  • fscanf&fprintf:是应用于所有的标准输入流和输出流的格式化输出语句
  • sscanf&sprinf:是可以把结构化的数据转换为字符串,也可以把字符串中读取结构化的数据

5.文件的随机读写(fseek&ftell &rewind)

int fseek( FILE *stream, long offset, int origin );

  • origin有3个选项
    1. SEEK_SET:设置指定偏移量
    2. SEEK_CUR:从起始位置设置偏移量
    3. SEEK_END:从结束位置设置偏移量
#include <stdio.h>

int main()
{
	FILE* pf = fopen("test.txt", "r");
    if (pf == NULL)
	{
		return 1;
	}
	printf("%c\n",fgetc(pf));
	printf("%c\n",fgetc(pf));

	//人文件指针回到偏移量为0的位置
	fseek(pf, 0 SEEK_SET);//让文件指针指向起始位置偏移量为0的位置
	printf("%c\n", fgetc(pf));
	fseek(pf, 2, SEEK_CUR);//让文件指针指向起始位置偏移量往后+2的位置
	printf("%c\n", fgetc(pf));
	fseek(pf, -2, SEEK_END);//让文件指针指向末尾前2两个位置
	printf("%c\n", fgetc(pf));
	
	fclose(pf);
    
	return 0;
}

在这里插入图片描述

ftell函数

返回文件指针相对于起始位置的偏移量

long ftell( FILE *stream );
#include <stdio.h>

int main()
{
	FILE* pf = fopen("test.txt", "r");
	if (pf == NULL)
	{
		return 1;
	}
	fgetc(pf);
	fgetc(pf);
	printf("%d\n", ftell(pf));
	//人文件指针回到偏移量为0的位置
	fseek(pf, 0, SEEK_SET);
	printf("%d\n", ftell(pf));
	
	fclose(pf);
	
	return 0;
}

rewind 函数

让文件指针的位置回到文件的起始位置

void rewind ( FILE * stream );
#include <stdio.h>

int main()
{
	FILE* pf = fopen("test.txt", "r");
	if (pf == NULL)
	{
		return 1;
	}
	fgetc(pf);
	fgetc(pf);
	printf("%d\n", ftell(pf));
	//人文件指针回到偏移量为0的位置
	rewind(pf);
	printf("%d\n", ftell(pf));
	
	fclose(pf);
	
	return 0;
}

6. 文件结束判定

feof是用来判断文件是否结束的,但容易被人错误使用。

int feof( FILE *stream );

注意:在文件读取过程中,不能使用feof函数的返回值直接用来判断文件的是否结束,而是将该函数用于当文件读取结束的时候,判断是读取失败结束,还是遇到文件末尾结束

  1. 文本文件读取是否结束,判断返回值是否为EOF,又或者是NULL。
    • fgetc判断是否为EOF
    • fgets判断返回值是否为NULL
  2. 二进制文件的读取结束判断,判断返回值是否小于实际要读取的个数
    • fread判断返回值是否小于实际要读取的个数

函数使用示例

判断文本文件结束

#include <stdio.h>
#include <string.h>
#include <errno.h>

int main()
{
	FILE* pf = fopen("test.txt", "r");//读取的方式
	if (pf == NULL)
	{
		return 1;
	}
	char* c = 0;
	char  buffer[20] = { 0 };
	while ((c = fgets(buffer, 20, pf)) != NULL)
	{
		printf("%s", buffer);
	}
	if (feof(pf))
	{
		printf("读取到文件末尾正常结束");
	}
	else
	{
		printf("错误退出 %s", strerror(errno));
	}
	fclose(pf);
	
	return 0;
}

判断二进制文件结束

#include <stdio.h>
#include <string.h>
#include <errno.h>

typedef struct  Stu
{
	char name[20];
	char sex[10];
	int age;
}Stu;
int main()
{
	FILE* pf = fopen("test.txt", "rb");//二进制读取的方式
	if (pf == NULL)
	{
		return 1;
	}
	int count = 0;
	Stu s = { 0 };
	while ((count = fread(&s, sizeof(Stu), 1, pf)) != 0)
	{
		printf("%s %s %d\n", s.name, s.sex, s.age);
	}
	if (feof(pf))
	{
		printf("文件正常读取完毕结束\n");
	}
	else
	{
		printf("文件读取错误异常结束 %s\n", strerror(errno));
	}
	fclose(pf);

	return 0;
}

7. 文件在存储形式

通过上述了解,C语言的文件操作基本就是围绕着文本文件二进制文件进行操作.

他们都是数据文件,而数据在内存中是以二进制存储的,如果不进行转换直接输出到磁盘,就是二进制文件

如果要在磁盘中以ASII码的形式存储,则需要在存储前转换,以ASCII字符的形式存储就是文本文件
一个数据在内存中是怎么存储的呢?

字符一律是以ASCII形式存储,数值类型既可以用ASCII形式存储,也可以使用二进制形式存储。

假设又一个整数1000,如果要以ASCII码的形式输出到磁盘,则磁盘中占用4个字节(一个字符占一个字节),而以二进制的形式输出,则在磁盘上只占4个字节(VS2019平台上)

由下图VS2019监视是以十六进制显示的,e8 03 00 00转换为二进制就是1110‬1000‬ 00000011 00000000 00000000,应为我们这里是小端存储所以二进制因该是00000000 00000000 00000011 11101000

在这里插入图片描述

在这里插入图片描述

测试代码

#include <stdio.h>

int main()
{
	int a = 1000;
	
	FILE* pf = fopen("test.txt", "wb");
	fwrite(&a, 4, 1, pf);

	fclose(pf);
    pf = NULL;
	return 0;
}

8. 文件缓冲区

C语言标准采用缓冲文件系统处理数据文件,缓冲文件系统指的是系统自动的在内存中为程序中为程序中每一个正在使用的文件开辟一块文件缓冲区。从内存向磁盘输出数据会先送到内存中的缓冲区,装满缓冲区后才一起送到磁盘上,如果从磁盘向计算机读入数据吗,则从磁盘文件中读取数据输入到内存缓冲区(填满缓冲区),然后再从缓冲区逐个地将数据送到程序数据区,缓冲区的大小由编译器决定的。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-t0Gh1wZg-1670326098573)(assets/1670126909085.png)]

为什么要有文件缓冲区?

假设没有缓冲区,我们每写入或者读取一个字符,都要打断操作系统进行磁盘的写入和读取,就会频繁的进行写入和读取。而读取写入磁盘速度是较慢的,

文件缓冲区是在内存中的,而内存的读写速度比磁盘快好几个数量级,只需要把数据写入到文件缓冲区中,等缓冲区满了再写入到磁盘中,这样可以减少磁盘的IO次数,提高的运行速度。

文件缓冲区目的是缓和CPU 与 I/O 设备间速度不匹配的矛盾。减少对 CPU 的中断频率,放宽对 CPU 中断响应时间的限制。提高 CPU和 I/O 设备之间的并行性,这有点类似于生产者消费者模型。

验证文件缓冲区

#include <stdio.h>
#include <windows.h>

int main()
{
	FILE*pf = fopen("test.txt", "w");
	fputs("abcdef", pf);//先将代码放在输出缓冲区
	printf("睡眠10秒-已经写数据了,打开test.txt文件,发现文件没有内容\n");
	Sleep(10000);
	printf("刷新缓冲区\n");
	fflush(pf);//刷新缓冲区时,才将输出缓冲区的数据写到文件(磁盘)

	printf("再睡眠10秒-此时,再次打开test.txt文件,文件有内容了\n");
	Sleep(10000);
	fclose(pf);
	//注:fclose在关闭文件的时候,也会刷新缓冲区
	pf = NULL;

	return 0;
}

存中的缓冲区,装满缓冲区后才一起送到磁盘上,如果从磁盘向计算机读入数据吗,则从磁盘文件中读取数据输入到内存缓冲区(填满缓冲区),然后再从缓冲区逐个地将数据送到程序数据区,缓冲区的大小由编译器决定的。

在这里插入图片描述

为什么要有文件缓冲区?

假设没有缓冲区,我们每写入或者读取一个字符,都要打断操作系统进行磁盘的写入和读取,就会频繁的进行写入和读取。而读取写入磁盘速度是较慢的,

文件缓冲区是在内存中的,而内存的读写速度比磁盘快好几个数量级,只需要把数据写入到文件缓冲区中,等缓冲区满了再写入到磁盘中,这样可以减少磁盘的IO次数,提高的运行速度。

文件缓冲区目的是缓和CPU 与 I/O 设备间速度不匹配的矛盾。减少对 CPU 的中断频率,放宽对 CPU 中断响应时间的限制。提高 CPU和 I/O 设备之间的并行性,这有点类似于生产者消费者模型。

验证文件缓冲区

#include <stdio.h>
#include <windows.h>

int main()
{
	FILE*pf = fopen("test.txt", "w");
	fputs("abcdef", pf);//先将代码放在输出缓冲区
	printf("睡眠10秒-已经写数据了,打开test.txt文件,发现文件没有内容\n");
	Sleep(10000);
	printf("刷新缓冲区\n");
	fflush(pf);//刷新缓冲区时,才将输出缓冲区的数据写到文件(磁盘)

	printf("再睡眠10秒-此时,再次打开test.txt文件,文件有内容了\n");
	Sleep(10000);
	fclose(pf);
	//注:fclose在关闭文件的时候,也会刷新缓冲区
	pf = NULL;

	return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/68118.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

兄弟机床联网

一、设备信息确认 1、确认型号 看面板颜色&#xff1a; 面板如果是彩色屏幕&#xff0c;大概率是可以做联网采集的。如果是黑白屏则需要进一步确认设备名牌。 看名牌&#xff1a; 名牌一般在设备后面&#xff0c;可以看到数控系统的品牌&#xff0c;一般C00和B00都是可以直接…

怎么写综述类论文? - 易智编译EaseEditing

一、确定综述的主题 每篇综述都应该有一个观点&#xff0c;即想要表达的事物。一篇综述不是简单的对相关发现的罗列。综述的真正功能是迈出下一步。已有的研究告诉了我们什么&#xff1f;以及我们下一步要怎么做&#xff1f; 确定综述的主题在撰写过程中是最重要的一步。这会…

快速上手几个Linux命令

Linux操作系统有很多功能&#xff0c;我们有很多方式可以使用这些功能&#xff0c;其中最简单和直接的方式就是命令行&#xff08;Command Line&#xff09; 用户与密码 当我们打开一个新系统的时候&#xff0c;第一件要做的事就是登录。系统默认有一个 Administrator 用户&a…

Vue学习:Vue中的数据代理

<!-- 准备容器 --><div idroot> <h2>学校名称&#xff1a;{{name}}</h2><h2>学校地址&#xff1a;{{adress}}</h2></div><script>const vm new Vue({ el: #root,data: {name:Jhon,adress:street 10},});</script> vm上…

8.javase_数组2

一 . 二维数组 (1)二维数组 元素为一维数组的数组 (2)定义格式&#xff1a; 数据类型[][] 变量名; int[][] arr; 数据类型 变量名[][]; int arr[][]; 数据类型[] 变量名[]; int[] arr[]; 二.二维数组初始化 (1)静态初始化 格式&#xff1a;数据类型[][] 变量名 new 数据类型…

PNG怎么转成PDF格式?这两种方法一定要尝试一下

图片文件是我们经常使用到的一种文件类型&#xff0c;但是我们通常会有很多的图片需要同时进行发送&#xff0c;这时候发送给别人就不是很便利了&#xff0c;我们一般会需要通过微信进行发送&#xff0c;但是大家都知道&#xff0c;微信一次只能发送九张图片&#xff0c;有时候…

【CDC跨时钟域信号处理】快时钟域到慢时钟域-单bit

快时钟域到慢时钟域分两种情况&#xff1a; 1、允许采样丢失&#xff1a;直接采用同步器即可。 2、不允许采样丢失&#xff1a;原理是保证快时钟域的信号宽度满足一定的条件&#xff0c;使得慢时钟域有足够的时间采样到。 对于情况2有两种方法解决&#xff1a;①信号展宽边沿检…

接口管理测试繁琐复杂?何不试试Eolink

一、前言 作为一名测试从业者&#xff0c;深刻的明白接口测试在项目过程中是多么重要的一个环节。通过页面进行的UI测试会因为界面不稳定而导致用例维护非常困难。另外&#xff0c;在检查系统的安全性、稳定性上面也是尤为重要的环节&#xff0c;这些也是无法通过前端测试的&a…

react-native webstorm 无法启动 Android 模拟器

react-native webstorm 无法启动 Android 模拟器 一、问题描述 在 安装完 Android Studio 和 模拟器之后&#xff0c;WebStorm 启动 react-native 项目时提示如下&#xff1a; No emulators found as an output of emulator -list-avds.二、解决办法 官方环境安装说明&#x…

汽车OTA技术门槛提升,具备软硬一体化能力的Tier1优势凸显

在软件定义汽车的大背景下&#xff0c;无论是传统车企还是造车新势力都在加大OTA的布局力度&#xff0c;整车OTA的普及应用已经成为必然趋势。 高工智能汽车研究院监测数据显示&#xff0c;2022年1-6月中国市场&#xff08;不含进出口&#xff09;乘用车标配搭载OTA上险量为40…

移动硬盘raw怎么办?一招教你解决RAW格式的文件

RAW文件格式是一种特殊的文件格式。RAW表示未处理&#xff0c;因此RAW也指未格式化的磁盘。移动硬盘里有 RAW格式的文件。这是什么原因造成的&#xff1f;以及我们该如何把移动硬盘raw里面的文件给恢复回来&#xff1f;来看看下面的解说&#xff0c;一起寻找解决方法吧&#xf…

阿里云国际站云计算-负载均衡SLB介绍-unirech

阿里云国际站的负载均衡SLB&#xff08;Server Load Balancer&#xff09;是一种对流量进行按需分发的服务&#xff0c;通过将流量分发到不同的后端服务器来扩展应用系统的吞吐能力&#xff0c;并且可以消除系统中的单点故障&#xff0c;提升应用系统的可用性。 阿里云国际站的…

研究研究 ES_OEMCONVERT 标志

ES_OEMCONVERT 这个标志&#xff0c;主要是用在 16 位 Windows 系统上。下面是一篇 MSDN 上的文章中对它的一段描述&#xff1a; ES_OEMCONVERT 会导致输入到编辑控件中的文本从 ANSI 转换为 OEM&#xff0c;然后再转换回 ANSI。这可确保在应用程序调用 AnsiToOem 函数将编辑控…

【在Vue脚手架项目中使用axios】

目录 1. 安装axios 2. 在main.js中添加配置 1. 安装axios 首先&#xff0c;需要安装axios&#xff0c;则在终端窗口中&#xff0c;在当前项目文件夹下&#xff0c;执行安装命令&#xff1a; 如果没有权限进入C盘找到cmd的执行软件&#xff0c;用管理员启动&#xff0c;进入目…

作为外贸业务员,为什么我经常随机轻松 就“捡“到精准潜在客户

心里夹杂着很多情绪和想法&#xff0c;沉浸在客户背调里面走不出来&#xff0c;但我还是决定不得不暂停下得心应手的google背调&#xff0c;记录一下此时此刻的想法。 01 我曾好多次在文章里表露出做外贸业务背调是非常关键的一环&#xff0c;而在背调里一些细微的关键信息非常…

自适应滤波器更新算法-EP3

文章目录1、PNLMS和IPNLMS算法1.1 算法原理2.2 算法分析2、一种改进的时变参数的比例自适应滤波算法2.1 算法原理2.2 算法分析2.3 算法性能评价标准2.3.1 均方误差(Mean Square Error, MSE)2.3.2 失调(Misalignment, MIS)2.3.3 回声衰减系数(Echo Return Loss Enhancement, ERL…

【音视频开发】为什么无损音频会有44.1Khz这样的奇葩采样率?

文章目录一、 问题&#xff1a;为什么无损音频会有44.1Khz这样的奇葩采样率&#xff1f;二 、PCM流程2.1 PCM流程2.2 PCM量化方式2.2 量化位数2.3 比特率三、答疑解惑3.1 使用采样定理来解释3.2 以影片磁带录音&#xff1f;硬件限制而来的 44.1kHz3.3 关于44100和质数的关系四、…

【关于检查请求参数的基本有效性】

目录 检查请求参数的基本有效性 检查请求参数的基本有效性 在服务器端项目中&#xff0c;可以通过spring-boot-starter-validation对请求参数进行检查。 在客户端项目中&#xff0c;Element UI的示例表单中都有对各控件&#xff08;例如输入框、选择框等&#xff09;的检查。…

[附源码]Python计算机毕业设计Django校园生活服务平台

项目运行 环境配置&#xff1a; Pychram社区版 python3.7.7 Mysql5.7 HBuilderXlist pipNavicat11Djangonodejs。 项目技术&#xff1a; django python Vue 等等组成&#xff0c;B/S模式 pychram管理等等。 环境需要 1.运行环境&#xff1a;最好是python3.7.7&#xff0c;…

DBCO的PEG连接剂1480516-75-3,DBCO-PEG4-Maleimide(MAL)

DBCO-PEG4-Maleimide试剂反应原理&#xff1a; DBCO-PEG4-Maleimide是包含马来酰亚胺基团和DBCO部分的PEG连接剂。亲水性PEG间隔臂提高了在水缓冲液中的溶解度。马来酰亚胺基团与硫醇特异有效地反应&#xff0c;形成稳定的硫醚键。低质量将为改性分子添加间隔物&#xff0c;并…