当前位置: 首页 > news >正文

C语言笔记(通讯录)

目录

1.通讯录的架构

2.通讯录的功能

3.实现静态通讯录的功能步骤

3.1.创建通讯录数组

3.2.显示功能菜单

3.3.初始化通讯录

3.4.添加联系人的信息

3.5.显示联系人的信息

3.6.查找某个人的信息

3.7.删除某一个联系人信息

3.8.修改某一联系人的信息

3.9.按名字对联系人排序

3.10.清空通讯录

4.动态版本的实现

  4.1.重新定义通讯录

4.2.初始换通讯录

4.3.扩容和写入信息函数

5.将通讯录存入文件中

6.代码

6.1.contact.h文件

6.2.test.c文件

6.3.contact.c文件


  前言:

        本片通讯录分为两个版本;静态和动态版本,区别在静态版本就像是纸质的通讯录一样,无法增加容量;而动态版本使用动态内存函数(malloc、realloc)来实现扩容,达到使多少扩多少的目的,以节省内存空间。若有错误请批评指正。

1.通讯录的架构

        通讯录的编写分为了三个文件

1.test.c              主要编写 测试程序(程序运行的运行框架)

2.contact.c       主要编写测试程序中用到的自定义函数

3.contact.h      (1)包含相关的头文件

                         (2)创建全局变量

                         (3)声明contact.c中的函数

2.通讯录的功能

存储信息: 姓名 年龄 性别 地址 电话

静态版本实现功能:

  1.  显示功能菜单;
  2. 添加联系人的信息;
  3. 显示联系人的信息; 
  4. 查找某一个联系人信息;
  5. 删除某一联系人的信息;
  6. 修改某一联系人的信息;
  7. 按名字对联系人排序。

动态版本实现功能:

  1. 可以随着联系人的增多实现空间扩容。

3.实现静态通讯录的功能步骤

3.1.创建通讯录数组

        创建存储联系人信息的结构体 ,并重新命名为PeoInfo

typedef struct PeoInfo
{char name[20];int age;char sex[5];char addr[30];char tele[12];
}PeoInfo;

        创建通讯录数组;使用宏定义的通讯录大小以便查找和修改

#define MAX 1000//静态情况下定义的通讯录最大容量
typedef struct Contact
{PeoInfo data[MAX];//存放个人信息的int sz;           //当前已经存放几个人的信息
}contact;
3.2.显示功能菜单

        函数较为简单不做过多的说明;仅仅时printf函数的应用

void menu()
{printf("***********************************\n");printf("******  1.Add     2.Del     *******\n");printf("******  3.Search  4.Modify  *******\n");printf("******  5.Show    6.Sort    *******\n");printf("******  7.Clear   0.Exit    *******\n");printf("***********************************\n");
}
3.3.初始化通讯录

        初始化通讯录的目的就是将通讯录所占用的内存中的数据全部置为0。

void InitContact( contact* pc) 
{assert(pc);pc->sz = 0;memset(pc->data, 0, sizeof(pc->data));
}

memset函数  将 ptr 指向的内存块的前字节设置为指定

void * memset ( void * ptr, int value, size_t num );

ptr      指向要填充的内存块的指针

value  要设置的值。

num    要设置为该值的字节数

3.4.添加联系人的信息

        简单的说就是给一个信息数组输入数据,核心为scanf函数。

        第一个函数:判断通讯录是否还有空间;然后再调用信息输入函数;

        第二个函数:信息输入函数。

//添加信息函数
void AddContact(contact* pc)
{if (pc->sz == MAX){printf("通讯录已满");return;}ScanfInformation(pc);
}
//录入信息函数,调出来方便后续的使用
void ScanfInformation(contact* pc)
{printf("请输入名字\n");scanf("%s", pc->data[pc->sz].name);printf("请输入年龄\n");scanf("%d", &(pc->data[pc->sz].age));printf("请输入性别\n");scanf("%s", pc->data[pc->sz].sex);printf("请输入地址\n");scanf("%s", pc->data[pc->sz].addr);printf("请输入电话\n");scanf("%s", pc->data[pc->sz].tele);printf("输入完成\n");pc->sz++;printf("录入成功\n");
}
3.5.显示联系人的信息

        显示联系人的核心是printf函数应用;

-  为右对齐

+ 为左对齐

\t 为水平制表符

pc为结构体指针;使用->符号对结构体数据进行访问。

void ShowContact(const contact* pc)
{printf("%-10s\t %-10s\t %-9s\t %-9s\t %-10s\n","姓名" ,"年龄"," 性别"," 地址"," 电话");int i = 0;for (i = 0; i < pc->sz; i++){printf("%-10s\t %-10d\t %-10s\t %-10s\t %-10s\n",pc->data[i].name,pc->data[i].age,pc->data[i].sex,pc->data[i].addr,pc->data[i].tele);}}
3.6.查找某个人的信息

思路

  1. 找到这个人
  2. 然后显示信息
void SearchContact(contact* pc)
{//通过名字寻找联系人信息printf("请输入要搜索联系人的姓名\n");int pos = FindByName(pc);ShowContactone(pc, pos);
}int FindByName(contact* pc)
{char name[20] = { 0 };scanf("%s", name);int i = 0;for (i = 0; i < pc->sz; i++){if (strcmp(pc->data[i].name, name) == 0){	return i;}}return -1;
}void ShowContactone(const contact* pc,int pos)//打印一个人的信息
{printf("%-10s\t %-10s\t %-9s\t %-9s\t %-10s\n", "姓名", "年龄", " 性别", " 地址", " 电话");printf("%-10s\t %-10d\t %-10s\t %-10s\t %-10s\n",pc->data[pos].name,pc->data[pos].age,pc->data[pos].sex,pc->data[pos].addr,pc->data[pos].tele);
}
3.7.删除某一个联系人信息

        按照名字来找联系人,并显示这个人的信息;主要就是strcmp函数比较

strcmp函数  比较两个字符串

int strcmp ( const char * str1, const char * str2 );

  1. 函数1:要找个人的大体思路;
  2. 函数2:按名字找人;
  3. 函数3:输出这个人的信息。
int FindByName(contact* pc)
{char name[20] = { 0 };scanf("%s", name);int i = 0;for (i = 0; i < pc->sz; i++){if (strcmp(pc->data[i].name, name) == 0){	return i;}}return -1;
}void DelContact(contact* pc)//找到删除人的名字然后向前递增一下
{printf("请输入要删除的人的名字\n");int del = FindByName(pc);//然后信息覆盖if (del >= 0){for (;  del < pc->sz; del++){pc->data[del] = pc->data[del + 1];}pc->sz--;printf("删除成功\n");}else if (del < 0){printf("未找到该联系人\n");}
}
3.8.修改某一联系人的信息

思路

  1. 找到这个人
  2. 重新录入信息
    void ModifyContact(contact* pc)
    {printf("请输入要修改联系人的姓名\n");int pos = FindByName(pc);if (-1 == pos){printf("未查找到此人\n");}else //修改某人的信息{printf("请输入名字\n");scanf("%s", pc->data[pos].name);printf("请输入年龄\n");scanf("%d", &(pc->data[pos].age));printf("请输入性别\n");scanf("%s", pc->data[pos].sex);printf("请输入地址\n");scanf("%s", pc->data[pos].addr);printf("请输入电话\n");scanf("%s", pc->data[pos].tele);printf("输入完成\n");printf("修改成功,修改信息如下\n");ShowContactone(pc, pos);}
    }int FindByName(contact* pc)
    {char name[20] = { 0 };scanf("%s", name);int i = 0;for (i = 0; i < pc->sz; i++){if (strcmp(pc->data[i].name, name) == 0){	return i;}}return -1;
    }

3.9.按名字对联系人排序

qsort函数

void qsort (void* base, size_t num, size_t size,int (*compar)(const void*,const void*));

base 指向要排序的数组的第一个对象的指针,转换为 .void*

num 指向的数组中的元素数。

size 指向的数组中的元素数。(以字节为单位)

int (*compar)(const void*,const void*)

指向比较两个元素的函数的指针。
此函数

int CompareByName(const void * a, const void * b)
{return (((PeoInfo*)a)->name ,((PeoInfo*)b)->name);
}
void SortContact(contact* pc) 
{assert(pc);if (pc->sz == 0){printf("通讯录没有人\n");return;}qsort(pc->data, pc->sz, sizeof(pc->data[0]),CompareByName);//数组 数组的大小 数组有几个元素,数组元素的大小printf("排序完成\n");}
3.10.清空通讯录

        思路:通讯录群不清零和初始化一样所以

void DestoryContact(contact* pc)
{InitContact(pc);
}

4.动态版本的实现

  4.1.重新定义通讯录
typedef struct Contact
{PeoInfo* data;//存放个人信息的int sz;           //当前已经存放几个人的信息int capacity;     //目前通讯录的容量
}contact;
4.2.初始换通讯录

        使用malloc函数开辟空间;

1.功能:

  malloc:向内存申请一块连续可用的空间,返回指向这块空间起始的指针;

  free:   释放动态开辟的内存。

2.使用形式

void* malloc (size_t size);
void free (void* ptr);

1.void* 返回值类型为空指针,需要强转换再使用,申请成功返回内存块起始指针,申请内存失败,返回位空指针;

2.size 内存块的大小,字节位单位,size_t无符号整型;

注意:

1.malloc函数申请的空间是不会初始化的,内存块不初始化是随机值。

2.在free释放内存块之后,void* 函数的返回值保留之前的开辟内存块的时候指针变量,

如果再访问就是非法访问了,因此使用完内存空间要将返回值置为NULL,可看示例。

#define DEFAULT_SZ 3 //初始开辟空间
#define INC_SZ 3     //每次扩容的大小void InitContact2(contact* pc)
{assert(pc);pc->data = (PeoInfo*)malloc(DEFAULT_SZ * sizeof(PeoInfo));if (pc == NULL){perror("Init_Contact2:");return;}pc->sz = 0;pc->capacity = DEFAULT_SZ;
}
4.3.扩容和写入信息函数
  1. 判断通讯录是否还有空间
  2. 有空间录入信息,无空间扩容后再录入新信息

realloc函数

        1.功能:Reallocate memory block,重新分配内存块的大小,扩展原有的内存块,或者申请新的内存块,

        特点:保留之前的内存中的数据。

        2.使用形式:

void* realloc (void* ptr, size_t size);
int Checkcapacity(contact* pc)
{//判断是否要扩容PeoInfo* str;if (pc->sz == pc->capacity){str = (PeoInfo*)realloc(pc->data, (pc->sz + INC_SZ) * sizeof(PeoInfo));if (str==NULL){perror("Check_capacity");printf("扩容失败\n");return 0;}else{pc->data = str;pc->capacity += INC_SZ;printf("扩容成功\n");}}return 1;
}void AddContact2(contact* pc)
{assert(pc);int ret = Checkcapacity(pc);if (0 == ret){return ;}//录入信息elseScanfInformation(pc);
}

5.将通讯录存入文件中

        选择使用二进制的存储较为方便

void SaveContact(contact* pc)
{assert(pc);//打开文件FILE* pf = fopen("contact.txt","wb");//二进制方打开if (NULL == pf){perror("SaveContact");return;}else {int i = 0;for (i = 0; i < pc->sz; i++){fwrite(pc->data + i, sizeof(PeoInfo), 1, pf);//写入}fclose(pf);pf == NULL;}
}

6.代码

6.1.contact.h文件
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>//定义变量
#define MAX 1000//静态情况下定义的通讯录最大容量
#define DEFAULT_SZ 3
#define INC_SZ 3typedef struct PeoInfo
{char name[20];int age;char sex[5];char addr[30];char tele[12];
}PeoInfo;
//创建通讯录
//typedef struct Contact
//{
//	PeoInfo data[MAX];//存放个人信息的
//	int sz;           //当前已经存放几个人的信息
//}contact;typedef struct Contact
{PeoInfo* data;//存放个人信息的int sz;           //当前已经存放几个人的信息int capacity;     //目前通讯录的容量
}contact;//功能菜单
void menu();
//初始化通讯录
//静态版本
void InitContact( contact* pc);
//动态版本
void InitContact2(contact* pc);
//输入信息
void AddContact(contact* pc);
//动态版本在输入信息之前容量增大需要扩容
int Checkcapacity(contact* pc);
void AddContact2(contact* pc);//显示通讯录
void ShowContact( contact* pc);
//删除指定人信息
void DelContact( contact* pc);
//寻找某一的联系人的联系方式
void SearchContact(contact* pc);
//修改某一的联系人的联系方式
void ModifyContact(contact* pc);
//排序
void SortContact(contact* pc);
//清空联系人 初始化
void DestoryContact(contact* pc);
//存储通讯录中的信息到文件中
void SaveContact(contact* pc);
6.2.test.c文件

        使用了一个枚举变量,和do……while循环以及swich()分支语句

#define _CRT_SECURE_NO_WARNINGS
#include "contact.h"
enum 
{Exit = 0,Add,     Del,Search,  Modify,Show,    Sort	
};
void menu();
int main()
{int input = 0;contact con;//初始化通讯录InitContact2(&con);do {menu();printf("            请选择模式\n");scanf("%d", &input);switch(input){case Add:AddContact2(&con);break;case Del:	DelContact(&con);break;case Search:SearchContact(&con);break;case Modify:ModifyContact(&con);break;case Show:ShowContact(&con);break;case Sort:SortContact(&con);break;case Exit:SaveContact(&con);DestoryContact(&con);printf("退出编辑\n");default:printf("输入错误,请重新输入\n");}} while (input);return 0;
}
6.3.contact.c文件

        contact.c文件起始就是函数来回调用;模块化更为简单易懂,看着方便。

#include "contact.h"//功能菜单
void menu()
{printf("***********************************\n");printf("******  1.Add     2.Del     *******\n");printf("******  3.Search  4.Modify  *******\n");printf("******  5.Show    6.Sort    *******\n");printf("******  7.Clear   0.Exit    *******\n");printf("***********************************\n");}
//按照名字寻找某人
int FindByName(contact* pc)
{char name[20] = { 0 };scanf("%s", name);int i = 0;for (i = 0; i < pc->sz; i++){if (strcmp(pc->data[i].name, name) == 0){	return i;}}return -1;
}
void ScanfInformation(contact* pc)
{printf("请输入名字\n");scanf("%s", pc->data[pc->sz].name);printf("请输入年龄\n");scanf("%d", &(pc->data[pc->sz].age));printf("请输入性别\n");scanf("%s", pc->data[pc->sz].sex);printf("请输入地址\n");scanf("%s", pc->data[pc->sz].addr);printf("请输入电话\n");scanf("%s", pc->data[pc->sz].tele);printf("输入完成\n");pc->sz++;printf("录入成功\n");
}//初始化通信录//清空通讯录
void InitContact( contact* pc) 
{assert(pc);pc->sz = 0;memset(pc->data, 0, sizeof(pc->data));
}
//动态版本
void InitContact2(contact* pc)
{assert(pc);pc->data = (PeoInfo*)malloc(DEFAULT_SZ * sizeof(PeoInfo));if (pc == NULL){perror("Init_Contact2:");return;}pc->sz = 0;pc->capacity = DEFAULT_SZ;
}
//录入信息 静态 不再扩容的情况
//检查容量
int Checkcapacity(contact* pc)
{//判断是否要扩容PeoInfo* str;if (pc->sz == pc->capacity){str = (PeoInfo*)realloc(pc->data, (pc->sz + INC_SZ) * sizeof(PeoInfo));if (str==NULL){perror("Check_capacity");printf("扩容失败\n");return 0;}else{pc->data = str;pc->capacity += INC_SZ;printf("扩容成功\n");}}return 1;
}void AddContact2(contact* pc)
{assert(pc);int ret = Checkcapacity(pc);if (0 == ret){return ;}//录入信息elseScanfInformation(pc);
}void AddContact(contact* pc)
{if (pc->sz == MAX){printf("通讯录已满");return;}ScanfInformation(pc);
}
//录入信息 静态 不再扩容的情况//显示通讯录
void ShowContact(const contact* pc)
{printf("%-10s\t %-10s\t %-9s\t %-9s\t %-10s\n","姓名" ,"年龄"," 性别"," 地址"," 电话");int i = 0;for (i = 0; i < pc->sz; i++){printf("%-10s\t %-10d\t %-10s\t %-10s\t %-10s\n",pc->data[i].name,pc->data[i].age,pc->data[i].sex,pc->data[i].addr,pc->data[i].tele);}}
void ShowContactone(const contact* pc,int pos)//打印一个人的信息
{printf("%-10s\t %-10s\t %-9s\t %-9s\t %-10s\n", "姓名", "年龄", " 性别", " 地址", " 电话");printf("%-10s\t %-10d\t %-10s\t %-10s\t %-10s\n",pc->data[pos].name,pc->data[pos].age,pc->data[pos].sex,pc->data[pos].addr,pc->data[pos].tele);
}//pos为位置信息
//删除某人的信息
void DelContact(contact* pc)//找到删除人的名字然后向前递增一下
{printf("请输入要删除的人的名字\n");int del = FindByName(pc);//然后信息覆盖if (del >= 0){for (;  del < pc->sz; del++){pc->data[del] = pc->data[del + 1];}pc->sz--;printf("删除成功\n");}else if (del < 0){printf("未找到该联系人\n");}
}void SearchContact(contact* pc)
{//通过名字寻找联系人信息printf("请输入要搜索联系人的姓名\n");int pos = FindByName(pc);ShowContactone(pc, pos);
}
void ModifyContact(contact* pc)
{printf("请输入要修改联系人的姓名\n");int pos = FindByName(pc);if (-1 == pos){printf("未查找到此人\n");}else //修改某人的信息{printf("请输入名字\n");scanf("%s", pc->data[pos].name);printf("请输入年龄\n");scanf("%d", &(pc->data[pos].age));printf("请输入性别\n");scanf("%s", pc->data[pos].sex);printf("请输入地址\n");scanf("%s", pc->data[pos].addr);printf("请输入电话\n");scanf("%s", pc->data[pos].tele);printf("输入完成\n");printf("修改成功,修改信息如下\n");ShowContactone(pc, pos);}
}
int CompareByName(const void * a, const void * b)
{return (((PeoInfo*)a)->name ,((PeoInfo*)b)->name);
}
void SortContact(contact* pc) 
{assert(pc);if (pc->sz == 0){printf("通讯录没有人\n");return;}qsort(pc->data, pc->sz, sizeof(pc->data[0]),CompareByName);//数组 数组的大小 数组有几个元素,数组元素的大小printf("排序完成\n");}
void DestoryContact(contact* pc)
{InitContact(pc);
}void SaveContact(contact* pc)
{assert(pc);//打开文件FILE* pf = fopen("contact.txt","wb");if (NULL == pf){perror("SaveContact");return;}else {int i = 0;for (i = 0; i < pc->sz; i++){fwrite(pc->data + i, sizeof(PeoInfo), 1, pf);}fclose(pf);pf == NULL;}
}

相关文章:

C语言笔记(通讯录)

目录 1.通讯录的架构 2.通讯录的功能 3.实现静态通讯录的功能步骤 3.1.创建通讯录数组 3.2.显示功能菜单 3.3.初始化通讯录 3.4.添加联系人的信息 3.5.显示联系人的信息 3.6.查找某个人的信息 3.7.删除某一个联系人信息 3.8.修改某一联系人的信息 3.9.按名字对联系…...

【Manus资料合集】激活码内测渠道+《Manus Al:Agent应用的ChatGPT时刻》(附资源)

DeepSeek 之后&#xff0c;又一个AI沸腾&#xff0c;冲击的不仅仅是通用大模型。 ——全球首款通用AI Agent的破圈启示录 2025年3月6日凌晨&#xff0c;全球AI圈被一款名为Manus的产品彻底点燃。由Monica团队&#xff08;隶属中国夜莺科技&#xff09;推出的“全球首款通用AI…...

Python 面向对象高级编程-定制类

目录 __str__ __iter__ __getitem__ __getattr__ __call__ 小结 看到类似__slots__这种形如__xxx__的变量或者函数名就要注意&#xff0c;这些在Python中是有特殊用途的。 __slots__我们已经知道怎么用了&#xff0c;__len__()方法我们也知道是为了能让class作用于len()…...

安装remixd,在VScode创建hardhat

在终端&#xff0c;以管理员身份&#xff0c;cmd 需要科学上网 npm install -g remix-project/remixd 在vscode插件中&#xff0c;安装solidity插件&#xff0c;是暗灰色那款 1.将nodeJs的版本升级至18以上 2.在vscode打开一个新的文件&#xff0c;在终端输入 npx hardhat 3.…...

开发环境搭建-02.后端环境搭建-熟悉项目结构

一.后端环境搭建...

Linux(Centos 7.6)命令详解:vi

1.命令作用 vi/vim 是Linux 系统内置不可或缺的文本编辑命令&#xff0c;vim 是vi 的加强版本&#xff0c;兼容vi 的所有指令&#xff0c;不仅能编辑文本&#xff0c;而且还具有shell 程序编辑的功能&#xff0c;可以不同颜色的字体来辨别语法的正确性。 2.命令语法 usage: …...

Ubuntu 20.04下配置VSCode以支持Eigen库开发

这里写目录标题 1. 安装Eigen库2. 配置VSCode的C开发环境3. 配置c_cpp_properties.json4. 编写代码并测试5. 配置tasks.json&#xff08;可选&#xff09;6. 运行程序总结 在VSCode中配置Eigen库&#xff08;用于线性代数、矩阵和向量运算的C库&#xff09;的步骤如下&#xff…...

正点原子[第三期]Arm(iMX6U)Linux移植学习笔记-2.1 uboot简介

前言&#xff1a; 本文是根据哔哩哔哩网站上“Arm(iMX6U)Linux系统移植和根文件系统构键篇”视频的学习笔记&#xff0c;在这里会记录下正点原子 I.MX6ULL 开发板的配套视频教程所作的实验和学习笔记内容。本文大量引用了正点原子教学视频和链接中的内容。 引用&#xff1a; …...

Android14 OTA差分包升级报kPayloadTimestampError (51)

由于VF 架构&#xff0c; 所以镜像的打包时间可能存在偏差&#xff0c; 如 boot.img 和 客制化的一些镜像打包 可能会在 vendor 侧进行打包。 而 与system 侧进行merge 时&#xff0c;时间戳比较乱&#xff0c;为了解决这个问题&#xff0c;让时间戳进行统一。 使用adb方式验证…...

PPT 技能:巧用 “节” 功能,让演示文稿更有序

在制作PPT时&#xff0c;你是否遇到过这样的情况&#xff1a;幻灯片越来越多&#xff0c;内容越来越杂&#xff0c;找某一页内容时翻得眼花缭乱&#xff1f;尤其是在处理大型PPT文件时&#xff0c;如果没有合理的结构&#xff0c;编辑和调整都会变得非常麻烦。这时候&#xff0…...

Mysql创建库、表练习

创建库 #创建 create database gc_novels default charsetutf8mb4;#default charsetutf8mb4 指定编码为utf-8#使用 use gc_novels#查看当前所在位置 select database(); 结果&#xff1a; 创建表 #创建 create table heros(-> id int,-> name varchar(50),-&…...

【原创】Ollama Test API For Linux/MacOS/Unix

安装Json解析工具 Linux/Unix sudo apt-get install jq -yMacOS brew install jq -y设置环境变量 export IP"192.168.250.229" export PORT"8080" export MODEL"deepseek-r1:7b"检查Ollama版本 curl http://"$IP":"$PORT&qu…...

盛铂科技 SLMF315频率综合器200MHz至15GHz 国产频综模块

在当今科技飞速发展的时代&#xff0c;射频技术在众多领域发挥着关键作用&#xff0c;从通信、雷达系统到科研实验&#xff0c;对频率综合器的性能要求日益严苛。以下是关于盛铂科技的 SLMF315 超低相位噪声频率综合器的介绍&#xff1a; SLMF315超低相位噪声0.2至15GHz频率综合…...

AI-前端开发webcrumbs.ai/frontend-ai,Fitten Code提高开发效率

1.webcrumbs.ai/frontend-ai Frontend AI by Webcrumbshttps://app.webcrumbs.ai/frontend-ai 可选择某一模版进行生成对应版本代码&#xff0c;减少开发量。 2.Fitten Code Vue AI 编程助手 Vue AI 编程助手 | 菜鸟教程https://www.runoob.com/vue2/fitten-code-vue2.htm…...

DeepSeek开源Day4:DualPipeEPLB技术详解

2 月 24 日&#xff0c;DeepSeek 启动 “开源周”&#xff0c;第四个开源的代码库为 DualPipe 与 EPLB&#xff08;一下发布了两个&#xff09;。DualPipe 与 EPLB 依然使用了大量与 Hopper 架构绑定的技术。 DualPipe 是由 DeepSeek-AI 团队开发的一种双向流水线并行通信算法&…...

代码随想录算法训练营第22天 | 组合 组合总和 电话号码的字母组合

77. 组合 77. 组合 - 力扣&#xff08;LeetCode&#xff09; class Solution {List<Integer> path new ArrayList<>();List<List<Integer>> result new ArrayList<>();public void backTracking(int n,int k,int startIndex){if(path.size() …...

Oracle19c进入EM Express(Oracle企业管理器)详细步骤

以下是使用Oracle 19c进入Oracle Enterprise Manager Database Express&#xff08;EM Express&#xff09;的详细步骤&#xff1a; ### **步骤 1&#xff1a;确认EM Express配置状态** 1. **登录数据库服务器** 使用Oracle用户或管理员权限账户登录操作系统。 2. **查看EM…...

Oracle 数据库基础入门(六):视图与索引的深入解析

在 Oracle 数据库的知识体系中&#xff0c;视图与索引是提升数据库操作效率和优化数据管理的重要工具。对于 Java 全栈开发者而言&#xff0c;熟练掌握视图与索引的运用&#xff0c;不仅能够增强数据库查询的性能&#xff0c;还能为构建高效稳定的后端应用提供有力支持。接下来…...

机器学习-随机森林解析

目录 一、.随机森林的思想 二、随机森林构建步骤 1.自助采样 2.特征随机选择 3构建决策树 4.集成预测 三. 随机森林的关键优势 ​**(1) 减少过拟合** ​**(2) 高效并行化** ​**(3) 特征重要性评估** ​**(4) 耐抗噪声** 四. 随机森林的优缺点 ​优点 ​缺点 五.…...

Qt添加MySql数据库驱动

文章目录 一. 安装MySql二.编译mysql动态链接库 Qt版本&#xff1a;5.14.2 MySql版本&#xff1a;8.0.41 一. 安装MySql 参考这里进行安装&#xff1a;https://blog.csdn.net/qq_30150579/article/details/146042922 将mysql安装目录里的bin&#xff0c;include和lib拷贝出来…...

MR的环形缓冲区(底层)

MapReduce的大致流程&#xff1a; 1、HDFS读取数据&#xff1b; 2、按照规则进行分片&#xff0c;形成若干个spilt&#xff1b; 3、进行Map 4、打上分区标签&#xff08;patition&#xff09; 5、数据入环形缓冲区&#xff08;KVbuffer&#xff09; 6、原地排序&#xff…...

RMAN备份bug-审计日志暴涨(select action from gv$session)

问题概述 /oracle 文件系统使用率过大&#xff0c;经过检查是审计日志过大,/oracle 目录 197G 审计日志占用70G&#xff0c;每6个小时产生大量审计日志&#xff0c;日志内容全是select action from gv$session &#xff0c;猜测可能跟备份有关&#xff0c; $>df -h /oracle…...

30秒从零搭建机器人管理系统(Trae)

1. 安装 [Trae官网】(https://www.trae.com.cn/) 2. 提示词 创建一个BS架构的机器人远程操控系统&#xff0c;具备机器人状态及位置实时更新&#xff0c;可以实现机器人远程遥控&#xff0c;可以对机器人工作日志进行统计分析&#xff0c;以及其它管理系统的常用功能3. 模型…...

OpenFeign 学习笔记

OpenFeign 学习笔记 一、基础入门 1.1 简介 OpenFeign 是基于声明式的 REST 客户端&#xff0c;用于简化服务间远程调用。&#xff08;编程式 REST 客户端&#xff08;RestTemplate&#xff09;&#xff09; 通过接口注解方式定义 HTTP 请求&#xff0c;自动实现服务调用。 …...

单例模式(线程案例)

单例模式可以分为两种&#xff1a;1.饿汉模式 2.懒汉模式 一.饿汉模式 //饿汉模式&#x1f447; class MySingleTon{//因为这是一个静态成员变量&#xff0c;在类加载的时候&#xff0c;就创建了private static MySingleTon mySingleTon new MySingleTon();//创建一个静…...

HttpServletRequest 和 HttpServletResponse 不同JDK版本的引入

java中&#xff0c;可能会用到JWT令牌校验&#xff0c; 这时&#xff0c;大概率会用到 HttpServletRequest&#xff0c;和 HttpServletResponse。 若为 JDK8&#xff0c;SpringBoot 2.7.3 的版本则引入&#xff1a; import javax.servlet.http.HttpServletRequest; import ja…...

数据安全VS创作自由:ChatGPT与国产AI工具隐私管理对比——论文党程序员必看的避坑指南

文章目录 数据安全VS创作自由&#xff1a;ChatGPT与国产AI工具隐私管理对比——论文党程序员必看的避坑指南ChatGPTKimi腾讯元宝DeepSeek 数据安全VS创作自由&#xff1a;ChatGPT与国产AI工具隐私管理对比——论文党程序员必看的避坑指南 产品隐私设置操作路径隐私协议ChatGPT…...

【JavaEE】SpringMVC简单练习

目录 一、计算器1.1 接口定义1.2 前端代码1.3 后端代码1.4 运行结果 二、⽤⼾登录2.1 需求2.2 接口定义2.3 前端页面2.4 后端代码2.5 结果 三、留⾔板3.1 需求:3.2 接口3.3 前端代码3.4 后端代码3.5 运行结果 四、图书管理系统4.1 需求4.2 接口定义4.3 后端代码 一、计算器 1.…...

文件上传漏洞:upload-labs靶场11-20

目录 pass-11 pass-12 pass-13 pass-14 pass-15 pass-16 pass-17 pass-18 pass-19 pass-20 pass-11 分析源代码 &#xff0c;发现上传文件的存放路径可控 if(isset($_POST[submit])){$ext_arr array(jpg,png,gif);$file_ext substr($_FILES[upload_file][name],st…...

苹果Siri升级遇阻,国行iPhone或将引入阿里、百度AI自救

AI整合进展缓慢 苹果正加速将生成式AI技术整合至Siri&#xff0c;但内部消息称其底层技术研发落后于竞争对手&#xff0c;进展未达预期。 国行iPhone将引入双AI模型 苹果计划在2025年中期为国行iPhone引入AI功能&#xff0c;目前已敲定与 阿里巴巴、百度 合作&#xff0c;用户…...

立即释放 Mac 空间!Duplicate File Finder 8 重复文件高速清理工具

Duplicate File Finder 专业的 Mac 重复文件清理工具。查找并删除重复的文件、文件夹&#xff0c;甚至相似的照片。 不要让无用的文件占用磁盘上的宝贵空间。 整理你的 Mac。用最好的重复文件查找器来管理你的文件集合。 扫描任何磁盘或文件夹 主文件夹、照片/音乐库、外部磁…...

ES时序数据库的性能优化

本文主要是讲解了Elasticsearch数据库的优化&#xff0c;大家可以看一下。因为当时实操中涉及了6版本和7版本的一起优化&#xff0c;所以内容上大家自行区分一下。 一、基础设置 1. jvm.options参数详解 不同版本java配置会不一样 -Xms12g -Xmx12g 说明&#xff1a; 将 Xms…...

第3章:启动界面与主界面设计

第3章:启动界面与主界面设计 学习目标 掌握SwiftUI中的启动界面(Splash Screen)设计与实现学习主界面的布局与导航结构设计实现灵感笔记的列表与网格视图掌握SwiftUI中的动画与过渡效果学习如何使用环境对象共享数据理论知识讲解 启动界面设计原则 启动界面(Splash Scre…...

c++ 作用域解析操作符::

目录 什么是 ::&#xff1f; 基本语法 主要用途 1. 访问全局作用域 2. 访问类的静态成员 3. 访问命名空间中的内容 4. 区分嵌套作用域 5. 在类中定义成员函数 注意事项 什么是 ::&#xff1f; 在C中&#xff0c;:: 是作用域解析操作符&#xff08;Scope Resolution O…...

JavaScript数据类型转换

在JavaScript编程中&#xff0c;由于其动态类型特性&#xff0c;经常需要在不同的数据类型之间进行转换。正确地执行类型转换不仅能够避免潜在的错误&#xff0c;还能提高代码的灵活性和可维护性。本文将探讨JavaScript中的常见数据类型转换方法&#xff0c;并提供一些实用的例…...

css错峰布局/瀑布流样式(类似于快手样式)

当样式一侧比较高的时候会自动换行&#xff0c;尽量保持高度大概一致&#xff0c; 例&#xff1a; 一侧元素为5&#xff0c;另一侧元素为6 当为5的一侧过于高的时候&#xff0c;可能会变为4/7分部dom节点 如果不需要这样的话删除样式 flex-flow:column wrap; 设置父级dom样…...

AI 技术 引入 RTK(实时动态定位)系统,可以实现智能化管理和自动化运行

将 AI 技术 引入 RTK(实时动态定位)系统,可以实现智能化管理和自动化运行,从而提高系统的精度、效率和可靠性。以下是 AI 技术在 RTK 系统中的应用实例: 一、AI 技术在 RTK 系统中的应用场景 1. 整周模糊度快速解算 问题:RTK 的核心是解算载波相位的整周模糊度,传统方法…...

【STM32F103ZET6——库函数】11.捕获红外信号

目录 红外原理 数据码 引导码 连发码 配置捕获引脚 使能引脚时钟 配置定时器 使能定时器时钟 配置输入捕获 中断优先级分组 配置定时器4中断 定时器中断使能 使能定时器 重写定时器中断服务函数 清空定时器中断标志位 例程 例程说明 main.h main.c HongWai…...

江科大51单片机笔记【9】DS1302实时时钟(上)

一、DS1302介绍 DS1302是由美国DALLAS公司推出的具有涓细电流充电能力的低功耗实时时钟芯片。它可以对年、月、日、周、时、分、秒进行计时&#xff0c;且具有闰年补偿等多种功能。RTC&#xff08;Real Time Clock&#xff09;&#xff1a;实时时钟&#xff0c;是一种集成电路…...

在Spring Boot + MyBatis中优雅处理多表数据清洗:基于XML的配置化方案

问题背景 在实际业务中&#xff0c;我们常会遇到数据冗余问题。例如&#xff0c;一个公司表&#xff08;sys_company&#xff09;中存在多条相同公司名的记录&#xff0c;但只有一条有效&#xff08;del_flag0&#xff09;&#xff0c;其余需要删除。删除前需将关联表&#xf…...

【计网】网络层

网络层 4.1 网络层提供的两种服务&#xff08;一&#xff09; 面向连接的虚电路服务&#xff08;二&#xff09; 无连接的数据报服务 4.2 IPv44.2.1 IPv4概述4.2.2 分类编址的IPv4地址4.2.3 划分子网的IPv4地址4.2.4 无分类编址的IPv4地址4.2.5 IPv4地址的应用规划&#xff08;…...

稳定性保障-前端

前端稳定性保障是确保应用在各种环境下都能 高效、稳定、无错误 运行的策略和方法。可以从 监控、测试、容灾、优化 等方面进行保障。 &#x1f4cc; 1. 监控 & 报警 实时监控 线上情况&#xff0c;及时发现问题。 ✅ 1.1 前端错误监控 • Sentry、Fundebug&#xff1a…...

批量给 Word 中的所有图片添加水印

如果要给一个 Word 文档加水印&#xff0c;很多小伙伴都能轻松的完成&#xff0c;因为使用 Office 就能轻松的操作&#xff0c;并且也有很多第三方的工具可以帮我们实现。那假如需要给 Word 中的每一张图片都添加上水印&#xff0c;那有什么比较好的方法实现呢&#xff1f;今天…...

jQuery UI 简介

jQuery UI 简介 引言 随着互联网技术的飞速发展,前端开发已经成为网站和应用程序建设的重要组成部分。jQuery UI 是一个基于 jQuery 的用户界面库,它为开发者提供了丰富的交互组件和视觉效果,使得创建具有吸引力和互动性的网页变得更加简单。本文将为您详细介绍 jQuery UI…...

`label` 标签的 `for` 属性详解

一、基本概念 label 标签的 for 属性用于将标签与表单控件&#xff08;如 input、select 等&#xff09;绑定&#xff0c;其值需与目标元素的 id 完全匹配。这种关联允许用户点击标签时触发控件交互&#xff08;如聚焦输入框或切换复选框&#xff09;&#xff0c;提升操作便捷…...

ArcGIS操作:10 投影坐标系转地理坐标系

应用情景&#xff1a;在计算shp面质心坐标的时&#xff0c;由于需要的坐标是经纬度&#xff0c;所以需要将投影坐标系转化为地理坐标系 1、打开工具箱 2、右侧&#xff1a;数据管理工具 → 投影和变换 → 要素 → 投影 3、选择投影的数据、输出路径、地理坐标系&#xff0c;点…...

【单片机通信技术】串口通信的几种方式与比较,详细解释SPI通信

一、介绍 串口通信是一种通过串行接口逐位传输数据的通信方式&#xff0c;广泛应用于嵌入式系统、工业控制、传感器网络等领域。 二、以下是几种常见的串口通信方式及其对比&#xff1a; 1.UART&#xff08;Universal Asynchronous Receiver/Transmitter&#xff09; 特点&am…...

DeepSeek开源Day5:3FSsmallpond技术详解

2 月 24 日&#xff0c;DeepSeek 启动 “开源周”&#xff0c;第四个开源的代码库为 3FS&smallpond&#xff08;又是一下发布了两个&#xff09;。 3FS&#xff08;Fire-Flyer File System&#xff09;是 DeepSeek 内部开发的一款高性能分布式文件系统&#xff0c;旨在为 A…...

常见的限流算法有哪些

计数器算法 原理&#xff1a;在固定的时间窗口内&#xff0c;对请求进行计数&#xff0c;当请求数量达到设定的阈值时&#xff0c;就开始限流&#xff0c;拒绝多余的请求。例如&#xff0c;设定 1 分钟的时间窗口内允许最多 100 个请求&#xff0c;那么在这 1 分钟内每来一个请…...

Android 低功率蓝牙之BluetoothGattCallback回调方法详解

BluetoothGattCallback 是 Android 中用于处理蓝牙低功耗&#xff08;BLE&#xff09;设备通信的核心回调类。它负责处理与 BLE 设备的连接、服务发现、数据读写等操作的结果。以下是对 BluetoothGattCallback 的详细解析&#xff1a; 1. onConnectionStateChange 触发时机&am…...