C语言 —— 指尖跃迁 刻印永恒 - 文件操作

news2025/4/18 14:38:28

目录

1. 什么是文件

1.1 程序文件

1.2 数据文件

1.3 文件名 

2. 二进制文件和文本文件

3. 文件的打开与关闭

3.1 流和标准流

3.2 文件指针

3.3 文件的打开与关闭

fopen 

fclose

4. 文件的顺序读写

4.1 fgetc和fputc 

 fgetc

fputc

4.2 fgets和fputs

fgets

fputs 

4.3 scanf / fscanf / sscanf

scanf 

fscanf

sscanf

4.4 printf / sprintf / fprintf

printf

fprintf

 sprintf

4.5 fread和fwrite

fread

fwrite

5. 文件的随机读写

fseek

ftell

rewind

6. 文件读取结束的判定

7. 文件缓冲区


1. 什么是文件

磁盘(硬盘)上的文件就是文件

        
但是在程序设计中,我们⼀般谈的文件有两种:程序文件、数据文件

1.1 程序文件

程序文件包括源程序文件(后缀为.c),目标文件(windows环境后缀为.obj),可执行程序(windows 环境后缀为.exe)

1.2 数据文件

就是程序运行时读写的数据,比如程序运行需要从中读取数据的文件,或者输出内容的文件

1.3 文件名 

⼀个文件要有⼀个唯⼀的文件标识(文件标识常被称为文件名),以便用户识别和引用,文件名包含3部分:文件路径 + 文件名主干 + 文件后缀

例如: c:\code\test.txt

c:\code\:表示文件路径      test:表示文件名主干      .txt:表示文件后缀


2. 二进制文件和文本文件

根据数据的组织形式,数据文件被称为文本文件和二进制文件

        

二进制文件二进制文件就是把内存中的数据按其在内存中存储的形式原样存储在磁盘上

        

文本文件:如果要求在外存上以ASCII码的形式存储,则需要在存储前转换。以ASCII字符的形式存储的⽂件就是文本文件

 

数据在内存中如何存储呢?

        

字符⼀律以ASCII形式存储,数值型数据既可以用ASCII形式存储,也可以使用二进制形式储

        

如有整数10000,如果以ASCII码的形式输出到磁盘,则磁盘中占用5个字节(每个字符⼀个字节),而⼆进制形式输出,则在磁盘上只占4个字节

#include<stdio.h>
#include<stdlib.h>
int main()
{
	int a = 100;
	FILE* pa = fopen("text.txt", "wb");
	fwrite(&a, 4, 1, pa);
	fclose(pa);
	pa == NULL;

	return 0;
}


3. 文件的打开与关闭

        

3.1 流和标准流

我们从键盘输入数据,向屏幕上输出数据,并没有打开流呢?那是因为C语言程序在启动的时候,默认打开了3个流:

        

stdin - 标准输⼊流,在⼤多数的环境中从键盘输⼊,scanf函数就是从标准输⼊流中读取数据

        
stdout - 标准输出流,⼤多数的环境中输出至显示器界⾯,printf函数就是将信息输出到标准输出流中

        
stderr - 标准错误流,⼤多数环境中输出到显示器界⾯

        

头文件为:

        

#include<stdio.h>

stdin、stdout、stderr 三个流的类型是: FILE* ,通常称为文件指针

        
C语言中,就是通过 FILE* 的文件指针来维护流的各种操作的
 

3.2 文件指针

文件类型指针简称件指针

每个被使用的文件都在内存中开辟了一个相应的文件信息区,用来存放文件的相关信息(如文件的名字,文件状态及文件当前的位置等)。这些信息是保存在一个结构体变量中的。该结构体类型是由系统声明的,取名FILE

我们可以在编译环境提供的 stdio.h 头⽂件中有以下的⽂件类型申明:

struct _iobuf {
	char* _ptr;
	int  _cnt;
	char* _base;
	int  _flag;
	int  _file;
	int  _charbuf;
	int  _bufsiz;
	char* _tmpfname;
};
typedef struct _iobuf FILE;

 不同的C编译器的FILE类型包含的内容不完全相同,但是大同小异

        

每当我们打开一个文件的时候,系统会根据文件的情况自动创建一个FILE结构的变量,并填充其中的信息,该变量就指向了文件信息区,通过该指针就可以找到文件

我们可以创造一个文件指针变量来接收打开文件后返回的变量,该指针变量就可以访问该文件

FILE*pf;

定义pf是一个指向FILE类型数据的指针变量。可以使pf指向某个文件的文件信息区(是一个结构体变量)

        

通过该文件信息区中的信息就能够访问该文件。也就是说,通过文件指针变量能够找到与它关联的文件

3.3 文件的打开与关闭

文件在读写之前应该先打开文件,在使用结束之后应该关闭文件

        

在编写程序的时候,在打开文件的同时,都会返回⼀个FILE*的指针变量指向该文件,也相当于建立了 指针和文件的关系

        

 ANSIIC规定使用fopen 函数来打开文件, fclose 来关闭文件

fopen 

fopen文档链接:

        

fopen - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fopen/?kw=fopen

//打开⽂件
FILE * fopen ( const char * filename, const char * mode );

其功能是使用给定的模式 mode 打开 filename 所指向的文件。文件顺利打开后,指向该流的文件指针就会被返回。如果文件打开失败则返回 NULL,并把错误代码存在 error 中

fclose

fclose文档链接:

        

fclose - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fclose/?kw=fclose

//关闭⽂件
int fclose ( FILE * stream );

返回值如果流成功关闭,fclose 返回 0,否则返回EOF(-1)(如果流为NULL,而且程序可以继续执行,fclose设定error number给EINVAL,并返回EOF)

当时用"w"、"wb"、"w+"、"wb+"这些打开方式时会清除文件原本存储的数据 

/* fopen fclose example */
#include <stdio.h>
int main()
{
	FILE* pFile;
	//打开⽂件
	pFile = fopen("myfile.txt", "w");
	//⽂件操作
	if (pFile != NULL)
	{
		fputs("fopen example", pFile);
		//关闭⽂件
		fclose(pFile);
	}
	return 0;
}


4. 文件的顺序读写

4.1 fgetc和fputc 

 fgetc

fgetc文档链接:

        

fgetc - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fgetc/?kw=fgetc

int fgetc ( FILE * stream );

从文件指针stream指向的文件中读取一个字符,该字符的ASCII值作为函数的返回值,读取一个字节后光标向后移一个字节,若返回值为EOF,说明文件结束,EOF是文件结束标志,值为-1 

int main()
{
	FILE* pb = fopen("text.txt", "r");//为输入打开一个文本文件
	if (pb == EOF)//判断是否打开成功
	{
		perror("fopen");
		return 1;
	}

	int ch = 0;
	while ((ch = fgetc(pb)) != EOF)//判断是否成功输入数据
	{
		printf("%c", ch);//成功读取则将外部文件中的数据输入到程序中
	}

	printf("\n");
	fclose(pb);//关闭文件
	pb == NULL;//将pb置为空指针

	return 0;
}

fputc

fputc文档链接:

        

fputc - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fputc/?kw=fputc

int fputc ( int character, FILE * stream );

返回值:

        

在正常调用情况下,函数返回写入文件的字符的ASCII码值,出错时,返回EOF(-1)。当正确写入一个字符或一个字节的数据后,文件内部写指针会自动后移一个字节的位置

int main()
{
	FILE* pa = fopen("text.txt", "w");//打开文件,打开方式为输出数据w
	if (pa == NULL)//判断是否打开成功
	{
		perror("fopen");
		return 1;
	}

	for (int i = 0; i < 26; i++)//成功打开后则把程序中的数据输出到外部文件中
	{
		int ret = fputc('a' + i, pa);
		printf("%c", ret);
	}

    //判断是否关闭文件成功
	if (fclose(pa) == EOF)
	{
		perror("fclose");
		return 1;
	}

	pa == NULL;//将pa置为空指针,防止野指针

	return 0;

4.2 fgets和fputs

 

fgets

fgets文档链接:

        

fgets - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fgets/?kw=fgets

char * fgets ( char * str, int num, FILE * stream );

从指定的流 stream 读取一行(每次最多只能从文件中读取一行内容,因为 fgets遇到换行符就结束读取,并把它存储在 str 所指向的字符串内。当读取 (n-1) 个字符时或者读取到换行符时又或者到达文件末尾时,它会停止,具体视情况而定

        

如果文件中的该行,不足n-1个字符,则读完该行就结束。如若该行(包括最后一个换行符)的字符数超过n-1,则fgets只返回一个不完整的行

返回值:

        

1. 如果成功,该函数返回str的头指针

        

2. 如果到达文件末尾或者没有读取到任何字符,str 的内容保持不变,并返回一个空指针

        

3. 如果发生错误,返回一个空指针

int main()
{
	FILE* pc = fopen("text.txt", "r");//为了输入数据打开文件
	if (pc == NULL)//判断是否打开成功
	{
		perror("fopen");
		return 1;
	}

	char arr[30] = { 0 };//创造数组
	//将读取到的字符串串存储到arr指向的字符串内,如果外部文件中有两行字符串,只需再读取一次
	fgets(arr, 26 + 1, pc);
	puts(arr);             //打印字符串
	fclose(pc);//关闭文件
	pc = NULL;//置为空指针

	return 0;
}

fputs 

fputs文档链接:

        

fputs - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fputs/?kw=fputs

int fputs ( const char * str, FILE * stream );

str:一个数组,包含了要写入的以空字符终止的字符序列

stream:指向 FILE 对象的指针,该 FILE 对象标识了要被写入字符串的流

函数功能是向指定的文件写入一个字符串(不自动写入字符串结束标记符‘\0’),成功写入一个字符串后,文件的位置指针会自动后移

        

该函数返回一个非负值,如果发生错误则返回 EOF(-1)

int main()
{
	FILE* pd = fopen("1.txt", "w");//为了将程序中的数据输入到外部文件,打开文件
	if (pd == NULL)//判断
	{
		perror("fopen");
		return 1;
	}

	char arr[20] = "sjjwdjtmkadkiana";//创建数组
	if ((fputs(arr, pd)) == EOF)//判断是否输入成功
	{
		perror("fputs");
		return 1;
	}
	
	if (fclose(pd) == EOF)//判断是否关闭成功
	{
		perror("fclose");
		return 1;
	}

	pd = NULL;
	return 0;
}

4.3 scanf / fscanf / sscanf

函数功能
scanf从标准输入流上读取格式化的数据
fscanf从指定的输入流上读取格式化的数据
sscanf在字符串中读取格式化的数据

         

scanf 

scanf文档链接:

        

cplusplus.com/reference/cstdio/scanf/https://cplusplus.com/reference/cstdio/scanf/

int scanf ( const char * format, ... );

 

函数的第一个参数是格式字符串,它指定了输入的格式,并按照格式说明符解析输入对应位置的信息并存储于可变参数列表中对应的指针所指位置

        

每一个指针要求非空,并且与字符串中的格式符一一顺次对应

fscanf

fscanf文档链接:

        

fscanf - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fscanf/?kw=fscanf        

fscanf:从指定的输入流上读取格式化的数据

int fscanf ( FILE * stream, const char * format, ... );

stream:要读取的文件指针,可以是标准输入流stdin、文件指针或者其他已经打开的文件流

format:格式控制字符串,指定了要读取的数据的格式和顺序

...:可变参数列表,用于接收读取的数据

fscanf其功能为根据数据格式(format),从输入流(stream)中读入数据,存储到...中,遇到空格和换行时结束,这与fgets有区别,fgets遇到空格不结束

int main()
{
	FILE* pb = fopen("text.txt", "r");//打开文件
	//判断是否打开成功
	if (pb == NULL)                   
	{
		perror("fopen1");
		return 1;
	}
	char b = 0; 
	char arr[10] = { 0 };

	//从文件流中读取数据格式化后分别放到b和arr中
	fscanf(pb, "%c\n%s", &b, arr);    

	printf("%c\n", b);                   
	printf("%s", arr);

	fclose(pb);                        
	pb = NULL;                         

	return 0;
}

sscanf

sscanf文档链接:

        

sscanf - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/sscanf/?kw=sscanf        

sscanf:在字符串中读取格式化的数据

 

int sscanf ( const char * s, const char * format, ...);

str:要解析的字符串      

format:格式字符串      

...:可变参数列表,用于接收解析后的数据

 返回值函数将返回成功赋值的字段个数,失败返回0 ,否则返回格式化的参数个数

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>

int main()
{
	char arr[] = "kiana";
	char arr1[10] = { 0 };

	//从字符串arr中读取数据放入arr1中
	sscanf(arr, "%s", arr1);
	printf("%s\n", arr1);

	int n = 0;

	sscanf("kiana 1134", "%s %d", arr1, &n);
	printf("%s %d", arr1, n);

	return 0;
}

sscanf的优点:

        

sscanf函数可以根据格式字符串的规则解析不同类型的数据,具有很高的灵活性

        

在使用sscanf函数时,要确保格式字符串与要解析的数据格式匹配,否则可能会导致解析错误或未定义的行为

        

需要注意的是,sscanf函数只会从字符串中解析数据,不会对字符串进行修改

4.4 printf / sprintf / fprintf

函数功能
printf      把数据以格式化的形式打印在标准输出流上
fprintf把数据以格式化的形式打印在指定的输出流上
sprintf把格式化的数据转化成字符串

printf

printf文档链接:

        

printf - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/printf/?kw=printf        

printf:把数据以格式化的形式打印在标准输出流上

int printf ( const char * format, ... );

fprintf

fprintf文档链接:

        

fprintf - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fprintf/?kw=fprintf        

fprintf:把数据以格式化的形式打印在指定的输出流上

int fprintf ( FILE * stream, const char * format, ... );

函数功能:根据指定的格式(format),向输出流(比如文件流)写入数据

        

返回值:如果写入文件成功,则返回写入的总字符数,如果写入文件失败,则返回负值

int main()
{
	FILE* pa = fopen("text.txt", "w");
	if (pa == NULL)
	{
		perror("fopen");
		return 1;
	}

	char arr[] = "kiana";
	int a = 10;

	//把格式化数据输出到文件中
	fprintf(pa, "%s %d", arr, a);

	fclose(pa);
	pa == NULL;

	return 0;
}

 sprintf

sprintf文档链接:

        

sprintf - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/sprintf/?kw=sprintf        

sprintf:把格式化的数据转化成字符串

int sprintf ( char * str, const char * format, ... );

函数功能是把格式化的数据写入某个字符串中,即发送格式化输出到 str 所指向的字符串 

返回值:

        

如果成功,则返回写入的字符总数,不包括字符串追加在字符串末尾的空字符

        

如果失败,则返回一个负数

int main()
{
	char arr[] = "kianachuji";
	int num = 20;
	char arr1[20] = { 0 };

	sprintf(arr1, "%s %d", arr, num);//把格式化的数据存放到arr1中
	puts(arr1);//打印arr1

	return 0;
}

4.5 fread和fwrite

fread

fread文档链接:

        fread - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fread/?kw=fread        

如果我们想要读取多行内容,就可以使用fread函数

size_t fread ( void * ptr, size_t size, size_t count, FILE * stream );

函数功能从给定输入流stream读取最多count个对象存储到指针ptr指向的数组中,每个对象size个字节,该函数以二进制形式对文件进行操作,不局限于文本文件

返回值

        

返回成功读取的对象个数,若出现错误或到达文件末尾,则可能小于count

        

若size或count为零,则fread返回零且不进行其他动作

        

fread不区分文件尾和错误,因此调用者必须用feof和ferror才能判断发生了什么

fwrite

fwrite文档链接:

        

fwrite - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fwrite/?kw=fwrite

size_t fwrite ( const void * ptr, size_t size, size_t count, FILE * stream );

函数功能把ptr指向的数组中的数据存储count个size字节的数据到输出流stream中,该函数以二进制形式对文件进行操作,不局限于文本文件

返回值:

        

如果成功,该函数返回一个 size_t 对象,表示元素的总数,该对象是一个整型数据类型

        

如果该数字与num参数不同,则会显示一个错误

int main()
{
	FILE* pa = fopen("1.txt", "wb");//以输出二进制数据打开文件
	int arr[10] = { 1,2,3,4,5,6,7,8,9,10 };

	//输入5个整型放在文件流中
	fwrite(arr, sizeof(arr), 5, pa);

	fclose(pa);
	pa == NULL;

	FILE* pb = fopen("1.txt", "rb");//以读取二进制数据打开文件
	int arr1[10] = { 0 };

	//从文件中读取三个整形存储到arr1中
	fread(arr1, 4, 3, pb);
	for (int i = 0; i < 10; i++)
	{
		printf("%d", arr1[i]);
	}

	fclose(pb);
	pb == NULL;

	return 0;
}


5. 文件的随机读写

文件的随机读写就是我们可以指定这个文件指针指向的位置,即指向第几个字符,然后从这个字符开始读写

fseek

fseek文档链接:

        

fseek - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/fseek/?kw=fseek

int fseek ( FILE * stream, long int offset, int origin );
                                   
stream:文件指针  

offset:相对于起始位置的偏移量

origin:起始位置

函数功能:根据文件指针的位置和偏移量来定位文件指针

        

返回值:成功返回0,失败返回一个非零值

int main()
{
	FILE* pa = fopen("1.txt", "w");//写
	if (pa == NULL)
	{
		perror("fopen");
		return 1;
	}

	//把字符串输出到文件流中
	fputs("abcdefgh", pa);
	//把光标移到起始位置向右偏移量为5的位置
	fseek(pa, 5, SEEK_SET);
	//把字符串123输出到文件流中
	fputs("123", pa);

	fclose(pa);
	pa == NULL;

	return 0;
}

ftell

ftell文档链接:

        

ftell - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/ftell/?kw=ftell

long int ftell ( FILE * stream );

函数功能:返回文件指针相对于起始位置的偏移量

        

返回值:成功则返回一个偏移量,失败则返回-1

int main()
{
	FILE* pa = fopen("text.txt", "w");//写
	if (pa == NULL)
	{
		perror("fopen");
		return 1;
	}

	//把字符串输出到文件流中
	fputs("abcdefgh", pa);
	//把光标移到起始位置向右偏移量为5的位置
	fseek(pa, 5, SEEK_SET);
	int a = ftell(pa);
	printf("%d", a);

	fclose(pa);
	pa == NULL;

	return 0;
}

rewind

rewind文档链接:

        

rewind - C++ Referencehttps://legacy.cplusplus.com/reference/cstdio/rewind/?kw=rewind

void rewind ( FILE * stream );

函数功能:让文件指针的位置回到文件的起始位置

int main()
{
	FILE* pa = fopen("1.txt", "w");//写
	if (pa == NULL)
	{
		perror("fopen");
		return 1;
	}

	//把字符串输出到文件流中
	fputs("abcdefgh", pa);
	//把光标移到起始位置向右偏移量为5的位置
	fseek(pa, 5, SEEK_SET);
	int a = ftell(pa);
	printf("重置之前偏移量为%d\n", a);

	rewind(pa);//把文件指针重置到文件起始位置
	int b = ftell(pa);
	printf("重置之后偏移量%d", b);

	fclose(pa);
	pa == NULL;

	return 0;
}


6. 文件读取结束的判定

注意:在文件读取过程中,不能用feof函数的返回值直接来判断文件的是否结束

 

feof 的作用是:当文件读取结束之后,判断是读取结束的原因是否是遇到文件尾结束

文本文件读取是否结束,判断返回值是否为 EOF ( fgetc ),或者 NULL ( fgets )

        

例如:

        

fgetc 判断是否为 EOF                fgets 判断返回值是否为 NULL 

文本文件举例:

#include <stdio.h>
#include <stdlib.h>
int main(void)
{
	int c; // 注意:int,⾮char,要求处理EOF
	FILE* fp = fopen("1.txt", "r");
	if (!fp) {
		perror("File opening failed");
		return EXIT_FAILURE;
	}

	//fgetc 当读取失败的时候或者遇到⽂件结束的时候,都会返回EOF
	while ((c = fgetc(fp)) != EOF) // 标准C I/O读取⽂件循环
	{
		putchar(c);
	}

	//判断是什么原因结束的
	if (ferror(fp))
		puts("I/O error when reading");
	else if (feof(fp))
		puts("End of file reached successfully");

	fclose(fp);
}

二进制文件的读取结束判断

二进制文件的读取结束判断,判断返回值是否小于实际要读的个数,例如:

        

fread判断返回值是否小于实际要读的个数,若出现错误或到达文件末尾,则可能小于count,write判断返回值是否等于实际要写入的数据个数

#include<stdio.h>

int main()
{
	FILE* pa = fopen("1.txt", "wb");//以输出二进制数据打开文件
	int arr[10] = { 1,2,3,4,5,6,7,8,9,10 };
	int ret = fwrite(arr, sizeof(arr), 5, pa);//输入5个整型放在文件流中
	if (ret != 5)//判断是否写入成功
	{
		perror("fwrite");
	}

	fclose(pa);//关闭文件
	pa == NULL;

	FILE* pb = fopen("text.txt", "rb");//以读取二进制数据打开文件
	int arr1[10] = { 0 };
	int rat = fread(arr1, 4, 3, pb);//从文件中读取三个整形存储到arr1中
	if (rat == 3)//判断返回值是否等于size
	{
		printf("返回值等于size\n");
	}
	else//不等于的话判断1.到达文件末尾2.读取出错
	{
		if (feof(pb))
		{
			printf("到达文件末尾");
		}
		else
			perror("fread error");
	}

	for (int i = 0; i < 10; i++)//输入
	{
		printf("%d", arr1[i]);
	}

	fclose(pb);
	pb == NULL;

	return 0;
}


7. 文件缓冲区

ANSIC标准采用“缓冲文件系统”处理的数据文件的,所谓缓冲⽂件系统是指系统自动地在内存中为 程序中每⼀个正在使用的文件开辟⼀块“文件缓冲区”,从内存向磁盘输出数据会先送到内存中的缓 冲区,装满缓冲区后才⼀起送到磁盘上

        

如果从磁盘向计算机读入数据,则从磁盘文件中读取数据输 入到内存缓冲区(充满缓冲区),然后再从缓冲区逐个地将数据送到程序数据区(程序变量等)。缓 冲区的大小根据C编译系统决定的

#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);//刷新缓冲区时,才将输出缓冲区的数据写到⽂件(磁盘) 
	//注:fflush 在⾼版本的VS上不能使⽤了 
	printf("再睡眠10秒-此时,再次打开test.txt⽂件,⽂件有内容了\n");

	Sleep(10000);
	fclose(pf);
	//注:fclose在关闭⽂件的时候,也会刷新缓冲区 

	pf = NULL;
	return 0;
}

 


 

完结撒花~
 

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

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

相关文章

网络安全与信息安全的区别​及共通

在数字化时代&#xff0c;网络安全与信息安全已成为保障个人、企业乃至国家正常运转的重要防线。尽管二者紧密相关且常被混为一谈&#xff0c;但实则存在显著差异。当然&#xff0c;它们也有一些相同点&#xff0c;比如都以保障数字环境下的安全为核心目标&#xff0c;均需要通…

【愚公系列】《Python网络爬虫从入门到精通》052-Scrapy 编写 Item Pipeline

&#x1f31f;【技术大咖愚公搬代码&#xff1a;全栈专家的成长之路&#xff0c;你关注的宝藏博主在这里&#xff01;】&#x1f31f; &#x1f4e3;开发者圈持续输出高质量干货的"愚公精神"践行者——全网百万开发者都在追更的顶级技术博主&#xff01; &#x1f…

【AI News | 20250416】每日AI进展

AI Repos 1、Tutorial-Codebase-Knowledge 自动分析 GitHub 仓库并生成适合初学者的通俗易懂教程&#xff0c;清晰解释代码如何运行&#xff0c;还能生成可视化内容来展示核心功能。爬取 GitHub 仓库并从代码中构建知识库&#xff1b;分析整个代码库以识别核心抽象概念及其交互…

GIS开发笔记(6)结合osg及osgEarth实现半球形区域绘制

一、实现效果 输入中心点坐标及半径&#xff0c;绘制半球形区域&#xff0c;地下部分不显示。 二、实现原理 根据中心点及半径绘制半球形区域&#xff0c;将其挂接到地球节点。 三、参考代码 void GlobeWidget::drawSphericalRegion(osg::Vec3d point,double radius) {// 使…

element-ui自定义主题

此处的element-ui为基于vue2.x的 由于https://element.eleme.cn/#/zh-CN/theme/preview&#xff08;element的主题&#xff09;报错503&#xff0c; 所以使用https://element.eleme.cn/#/zh-CN/component/custom-theme 自定义主题文档中&#xff0c;在项目中改变scss变量的方…

windows下使用nginx + waitress 部署django

架构介绍 linux一般采用nginx uwsgi部署django&#xff0c;在Windows下&#xff0c;可以取代uwsgi的选项包括Waitressa、Daphnea、Hypercoma和Gunicorna(通过WSLa 运行)。windows服务器一般采用nginx waitress 部署django&#xff0c;,他们的关系如下 django是WEB应用…

MySQL-多版本并发控制MVCC

文章目录 一、多版本并发控制MVCC二、undo log&#xff08;回滚日志&#xff09;二、已提交读三、可重复读总结 一、多版本并发控制MVCC MVCC是多版本并发控制&#xff08;Multi-Version Concurrency Control&#xff09;&#xff0c;是MySQL中基于乐观锁理论实现隔离级别的方…

目标检测与分割:深度学习在视觉中的应用

&#x1f50d; PART 1&#xff1a;目标检测&#xff08;Object Detection&#xff09; 1️⃣ 什么是目标检测&#xff1f; 目标检测是计算机视觉中的一个任务&#xff0c;目标是让模型“在图像中找到物体”&#xff0c;并且判断&#xff1a; 它是什么类别&#xff08;classif…

杰弗里·辛顿:深度学习教父

名人说&#xff1a;路漫漫其修远兮&#xff0c;吾将上下而求索。—— 屈原《离骚》 创作者&#xff1a;Code_流苏(CSDN)&#xff08;一个喜欢古诗词和编程的Coder&#x1f60a;&#xff09; 杰弗里辛顿&#xff1a;当坚持遇见突破&#xff0c;AI迎来新纪元 一、人物简介 杰弗…

STM32蓝牙连接Android实现云端数据通信(电机控制-开源)

引言 基于 STM32F103C8T6 最小系统板完成电机控制。这个小项目采用 HAL 库方法实现&#xff0c;通过 CubeMAX 配置相关引脚&#xff0c;步进电机使用 28BYJ-48 &#xff08;四相五线式步进电机&#xff09;&#xff0c;程序通过蓝牙连接手机 APP 端进行数据收发&#xff0c; OL…

第一个Qt开发的OpenCV程序

OpenCV计算机视觉开发实践&#xff1a;基于Qt C - 商品搜索 - 京东 下载安装Qt&#xff1a;https://download.qt.io/archive/qt/5.14/5.14.2/qt-opensource-windows-x86-5.14.2.exe 下载安装OpenCV&#xff1a;https://opencv.org/releases/ 下载安装CMake&#xff1a;Downl…

TCP 如何在网络 “江湖” 立威建交?

一、特点&#xff1a; &#xff08;一&#xff09;面向连接 在进行数据传输之前&#xff0c;TCP 需要在发送方和接收方之间建立一条逻辑连接。这一过程类似于打电话&#xff0c;双方在通话前需要先拨号建立连接。建立连接的过程通过三次握手来完成&#xff0c;确保通信双方都…

【小白训练日记——2025/4/15】

变化检测常用的性能指标 变化检测&#xff08;Change Detection&#xff09;的性能评估依赖于多种指标&#xff0c;每种指标从不同角度衡量模型的准确性。以下是常用的性能指标及其含义&#xff1a; 1. 混淆矩阵&#xff08;Confusion Matrix&#xff09; 定义&#xff1a;统…

数据结构——二叉树(中)

接上一篇&#xff0c;上一篇主要讲解了关于二叉树的基本知识&#xff0c;也是为了接下来讲解关于堆结构和链式二叉树结构打基础&#xff0c;其实无论是堆结构还是链式二叉树结构&#xff0c;都是二叉树的存储结构&#xff0c;那么今天这一篇主要讲解关于堆结构的实现与应用 堆…

02-MySQL 面试题-mk

文章目录 1.mysql 有哪些存储引擎、区别是什么?1.如何定位慢查询?2.SQL语句执行很慢,如何分析?3.索引概念以及索引底层的数据结构4.什么是聚簇索引什么是非聚簇索引?5.知道什么叫覆盖索引嘛 ?6.索引创建原则有哪些?7.什么情况下索引会失效 ?8.谈一谈你对sql的优化的经验…

#include<bits/stdc++.h>

#include<bits/stdc.h> 是 C 中一个特殊的头文件&#xff0c;其作用如下&#xff1a; 核心作用 ​​包含所有标准库头文件​​ 该头文件会自动引入 C 标准库中的几乎全部头文件&#xff08;如 <iostream>、<vector>、<algorithm> 等&#xff09;&…

在企业级部署中如何优化NVIDIA GPU和容器环境配置:最佳实践与常见误区20250414

在企业级部署中如何优化NVIDIA GPU和容器环境配置&#xff1a;最佳实践与常见误区 引言 随着AI和深度学习技术的迅速发展&#xff0c;企业对GPU加速计算的需求愈加迫切。在此过程中&#xff0c;如何高效地配置宿主机与容器化环境&#xff0c;特别是利用NVIDIA GPU和相关工具&…

Spring Boot 项目三种打印日志的方法详解。Logger,log,logger 解读。

目录 一. 打印日志的常见三种方法&#xff1f; 1.1 手动创建 Logger 对象&#xff08;基于SLF4J API&#xff09; 1.2 使用 Lombok 插件的 Slf4j 注解 1.3 使用 Spring 的 Log 接口&#xff08;使用频率较低&#xff09; 二. 常见的 Logger&#xff0c;logger&#xff0c;…

[react]Next.js之自适应布局和高清屏幕适配解决方案

序言 阅读前首先了解即将要用到的两个包的作用 1.postcss-pxtorem 自动将 CSS 中的 px 单位转换为 rem 单位按照设计稿尺寸直接写 px 值&#xff0c;由插件自动计算 rem 值 2.amfe-flexible 动态设置根元素的 font-size&#xff08;即 1rem 的值&#xff09;根据设备屏幕宽度和…

STM32H503CB升级BootLoader

首先&#xff0c;使用SWD接口&#xff0c;ST-LINK连接电脑和板子。 安装SetupSTM32CubeProgrammer_win64 版本2.19。 以下是接线和软件操作截图。