内存函数细节及实现

news2024/11/20 15:41:34

1、memcpy内存拷贝

不仅可以拷贝,还可以拷贝整型、结构体等,因为直接拷贝了内存。

因为不知道要拷贝的类型是什么,所以都用void*来接收。num是拷贝的字节数 

拷贝时可任意选择dest,src,以及字节数。返回void*类型的指针,使用时强制转换即可。

注意:假设拷贝整型时,如果不是4的倍数,拷贝时仅拷贝某个整型的一部分,而拷贝的这个部分又因为大小端字节序存储而不同,从而导致一些复杂情况甚至错误。因此尽量按需拷贝,一次拷贝完整,不要随意拷贝。

void* my_memcpy(void* dest, const void* src, size_t num)
{
	assert(dest && src);
	void* start = dest;
	while (num--)
	{
		*(char*)dest = *(char*)src;
		(char*)dest = (char*)dest + 1;
		(char*)src = (char*)src + 1;//转换为char*进行逐字节拷贝
	}
	return start;
}
int main()
{
	int arr1[10] = { 0 };
	int arr2[] = {1,2,3,4,5,6,7,8,9,10};
	my_memcpy(arr1, arr2+2, 20);
	//arr+2从第三个元素开始拷贝,arr为整型指针,+1跳过一个整型
}

  内存拷贝其实是一种不分类型的拷贝,我们之前在讲解冒泡bubble实现qsort函数时,也是利用void*,覆盖时强制类型转化为最小单元char*来进行逐字节覆盖的。以后在不分类型时都可考虑。 

与字符串拷贝与追加相同的是,当dest和src重叠时就会产生一些问题。当拷贝时改变了src的内容,进而导致后续拷贝的错误。

进一步的,我们对这种内存重叠的情况进行分析。

 

当我们要将1-5拷贝3-7时,可以从src的后面开始拷贝,即先拷贝5,再4,...直到全部拷贝

当我们要将3-7拷贝到1-5,可以从src的前面开始拷贝,即先拷贝3,再4,...直到全部拷贝

 当dest<src时,从src前部开始拷贝,反之从后。(不重叠时随意)

2、memmove

有了上述规律,我们可以将memcpy升级为memmove。即实现时加上上述规律。


void* my_memmove(void* dest, const void* src, size_t num)
{
	assert(dest && src);
	void* start = dest;
	if (dest>src)//后到前
	{
		while (num--)
		{
			*((char*)dest + num) = *((char*)src + num);
		}
	}
	else//前到后
	{
		while (num--)
		{
			*(char*)dest = *(char*)src;
			(char*)dest = (char*)dest + 1;
			(char*)src = (char*)src + 1;
		}
	}
}
int main()
{
	int arr1[] = { 1,2,3,4,5,6,7,8,9,10 };
	my_memcpy(arr1 + 2, arr1, 20);


}

升级过后就可以完成有内存覆盖的拷贝了。 

3、memset

将目标数组的指定个字节数设置为某值。 

传入的字符或ASCLL码值。

 把每个字节改为1,会发生截断。

 4、memcmp

 和strcmp类似,只是参数是void*类型,也可以指定字节数来进行比较,返回值0则相同,+-则为内存ASCLL码值的比较。

 

总结:

内存函数的优势:内存函数的实现是无关类型的,可以通过逐字节来实现,因为无关类型,所以函数参数返回值等要考虑使用void*类型,实现时可强制类型转换为char*后解引用或+-,接收时也是如此。

内存函数的劣势:因为不考虑具体类型而通过逐字节实现,我们还原到原来的类型时,常常会因为大小端字节序存储等原因,无法将这几个字节联系成一个整体,而进行单个的应用,从而导致一些麻烦和错误。

为了避开劣势,我们程序员在使用时应当充分考虑到使用的类型对应字节的整数倍,从而避免麻烦,快速方便的达到我们的需求。

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

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

相关文章

01什么是FPGA?

FPGA 是一种硬件可重构的体系结构。它的英文全称是Field Programmable Gate Array&#xff0c;中文名是现场可编程门阵列。 FPGA就是一个可以通过编程来改变内部结构的芯片&#xff0c;FPGA常年来被用作专用芯片&#xff08;ASIC&#xff09;的小批量替代品&#xff0c; 同时也…

PMP考试流程是怎么样的?

别的问题我可能不太了解&#xff0c;但考试流程我绝对是非常清楚了&#xff01;话不多说&#xff0c;直接放流程给到大家&#xff0c;好歹通过考试了&#xff0c;基本的情况还是能给大家讲解一下的。希望能够给有需要的同学提供点帮助。 先把考试的流程看仔细了&#xff0c;之…

核心乐理---音程名称

定义 音程是连个音之间的距离&#xff0c;是音乐中的距离&#xff0c;可以便于我们描述音符间的距离&#xff0c;便于与他人进行沟通交流。 就好像是厘米&#xff0c;米这些这些物理中的长度单位一样 度 度是音程的单位。 从一个音的名字念到另一个音的名字&#xff0c;一共念…

瑞幸“复制”拼多多

&#xff08;图片来源于网络&#xff0c;侵删&#xff09; 来源 | 螳螂观察 文 | 叶小安 在电商界&#xff0c;拼多多杀出阿里京东围剿重围&#xff0c;奠定现今电商行业“猫狗拼”三分天下的格局&#xff0c;这是多少后辈们参考的范本。 在咖啡界&#xff0c;瑞幸凭借低价…

ESP32基于Arduino框架,SD卡+MAX98357模块+MP3播放器

ESP32基于Arduino框架&#xff0c;SD卡MAX98357模块MP3播放器&#x1f3ac;原创作者的制作教程讲解以及源码&#xff1a; 35 ESP32之简单的完整功能SD卡MP3播放器的制作讲解&#xff08;ESP32-audioI2S库介绍&#xff09;- 基于Arduino链接&#xff1a;https://pan.baidu.com/s…

黑产系列02-黑产画像

黑产无利不起早&#xff0c;在利益的驱动下黑产几乎是屡禁不止&#xff0c;作为风控从业人员我们需要全方位的了解黑产&#xff0c;了解我们的对手&#xff0c;才能知己知彼&#xff0c;接下来我将结合我多年风控经验以及查阅的相关的资源&#xff0c;全方位介绍下黑产以及他们…

matplot绘制动图

import matplotlib.pyplot as plt from matplotlib.animation import FuncAnimation import numpy as np plt.rcParams[axes.unicode_minus] False plt.rcParams[font.sans-serif] SimHei# 准备数据 x np.linspace(0,3*np.pi,100) y1 np.sin(x) y2 np.cos(x)#创建画布和子图 …

Python用yield from 实现异步协程爬虫

文章目录一、什么是yield二、yield于列表的区别三、yield from 实现协程一、什么是yield 如果还没有怎么用过的话&#xff0c;直接把yield看做成一种特殊的return&#xff08;PS&#xff1a;本质 generator&#xff08;生成器&#xff09;&#xff09; return是返回一个值然后…

Python网络编程中getservbyport和getservbyname函数的用法

在Python的网络编程中&#xff0c;getservbyport()函数和getservbyname()函数是socket模块中的两个函数&#xff0c;因此在使用这两个函数时&#xff0c;需要导入socket模块。1 getservbyname()函数getservbyname()函数的作用是通过指定服务的名称获取该服务对应的端口号。相关…

BI工具+方案,这是要将大数据分析包了的节奏啊

BI工具是一个为企业提供大数据智能可视化分析功能板块的平台。虽然它提供了包括智能钻取、内存行列计算、多维动态分析等多种智能数据分析功能板块&#xff0c;但工具毕竟是工具&#xff0c;要真正地为企业所用&#xff0c;还需要针对企业的业务发展情况、数据分析需求等制定数…

用ode45解一个带有积分的微分方程(integro-differential equations)

一、问题提出: 这个方程来源于mathworks的论坛 l 这种方程叫 integro-differential equations ,大致是带有 integral term的微分方程。积分肯定是定积分,这类方程有的是变上限的积分,上下限是x或者其他微分的函数。 按照惯例,先分析。积分区间是0-1,x是自变量,y是应…

2022年终总结——工作第五年

2022是本命年&#xff0c;对我来说今年勉强可以算得上是一切顺利吧。 前几年的年终总结 先验收下去年的期望吧 去年的期望还是挺多的嗷&#x1f643; 1、关于订婚和云南一周游 ✅ 今年大概2月底开始上海疫情开始变得很严重&#xff0c;然后就是漫长的三个月封控&#xff0c;…

1.1.3 java学习的环境准备

文章目录1 相关文件准备及下载1.1 JDK下载1.2 开发工具下载1.2.1 eclipse1.2.2 idea2 JDK安装及配置2.1 JDK配置方法一2.2 JDK配置方法二3 eclipse软件安装及配置4 JDK JRE JVM解释&#xff1a;5 关于手写代码1 相关文件准备及下载 1.1 JDK下载 Oracle公司为常见的计算机系统…

【论文速递】ECCV2022 - ConMatch:置信度引导的半监督学习

【论文速递】ECCV2022 - ConMatch&#xff1a;置信度引导的半监督学习 【论文原文】&#xff1a;ConMatch: Semi-Supervised Learning with Confidence-Guided Consistency Regularization 获取地址&#xff1a;https://arxiv.org/abs/2208.08631博主关键词&#xff1a; 半监…

P8630 [蓝桥杯 2015 国 B] 密文搜索

题目描述 福尔摩斯从 X 星收到一份资料&#xff0c;全部是小写字母组成。 他的助手提供了另一份资料&#xff1a;许多长度为 88 的密码列表。 福尔摩斯发现&#xff0c;这些密码是被打乱后隐藏在先前那份资料中的。 请你编写一个程序&#xff0c;从第一份资料中搜索可能隐藏密码…

八大排序算法(C语言实现)

文章目录&#xff1a;1.排序的概念2.常见八大排序算法3.插入排序3.1直接插入排序3.2希尔排序4.选择排序4.1直接选择排序4.2.堆排序5.交换排序5.1冒泡排序5.2快速排序5.2.1快排递归实现5.2.1.1Hoare法&#xff08;霍尔法&#xff09;5.2.1.2挖坑法5.2.1.3双指针法5.2.2快排迭代实…

最火的聊天回复神器

客服高效回复容易收获用户的好感&#xff0c;也更容易将客户转化成功&#xff0c;借助聊天回复神器&#xff0c;可以助力客服高效快捷地回复。 前言 经常网购的用户&#xff0c;一定会发现在联系客服咨询产品相关问题时&#xff0c;刚把问题发出去&#xff0c;马上就可以收到客…

three.js入门-一些基础理论|大帅老猿threejs特训

前言 参加了threejs直播课。 本篇文章为入门理论部分笔记。 可以学到什么&#xff1a; 一、软能力 1. 系统全流程理解web3D 应用/数字孪生/元宇宙&#xff0c;程序开发与3D美术资源制作 2. 建立与3D美术团队良好沟通协作能力 3. 良好把控3D画面效果和性能平衡 4. 培养程…

数据分析师:星图Stagraph 2.1 Crack

Stagraph 是一个用于数据导入 - 数据整理 - 数据可视化的复杂软件工具。面向数据工程师、数据分析师、数据科学家、统计学家和其他“数据专业人员”的专业软件。在简单易用的可视化界面中提供最新数据科学工具的强大功能。采集 by Ω578867473 降低 降低处理数据的复杂性。使用…

作业帮:探索多云架构下的数据库集群解决方案

导语&#xff1a;面对业务多元、数据海量、数据库种类多样、多云架构复杂等痛点&#xff0c;该如何制定既能解决问题又能降本增效的数据库升级方案&#xff1f;作业帮作为实践者&#xff0c;从四方面分享其数据库选型过程与思考。以下为作业帮DBA刘强在DTCC大会中的讲述。 嘉宾…