💐 🌸 🌷 🍀 🌹 🌻 🌺 🍁 🍃 🍂 🌿 🍄🍝 🍛 🍤
📃个人主页 :阿然成长日记 👈点击可跳转
🚩 不能则学,不知则问,耻于问人,决无长进
🍭 🍯 🍎 🍏 🍊 🍋 🍒 🍇 🍉 🍓 🍑 🍈 🍌 🍐 🍍
🌸memcpy函数
#include
一、 memcpy函数的定义:
void * memcpy ( void * destination, const void * source, size_t num );
与strncmp区别是:参数方面:1.memcpy可以拷贝任意类型数据;2.num是字节数
二、memcpy函数的功能:
复制内存块
将字节数的值从源指向的位置直接复制到目标指向的内存块。
源指针和目标指针指向的对象的基础类型与此函数无关;结果是数据的二进制副本。
该函数不检查源中的任何终止空字符它总是==准确地复制字节数。
为避免溢出,目标和源参数指向的数组大小应至少为字节数,并且不应重叠(对于重叠的内存块,memmove 是一种更安全的方法)
三、memcpy函数模拟
#define _CRT_SECURE_NO_WARNINGS 1 #include<stdio.h> #include<assert.h> void* my_memcpy(void* dest, void* src, size_t num) { void* ret = dest; assert(dest); while (num--) { *(char*)dest = *(char*)src; dest = (char*)dest + 1; src = (char*)src + 1; } return ret; } int main() { int arr1[] = { 0,1,2,3,4,5,6,7,8,9 }; int arr2[20] = { 0 }; my_memcpy(arr2, arr1, 40); int i = 0; for (i = 0; i < 20; i++) { printf("%d\n", arr2[i]); } return 0; }
memcpy注意事项
1.函数memcpy从source的位置开始向后复制num个字节的数据到destination的内存位置。
2.这个函数在遇到 '\0'
的时候并不会停下来。
3.如果source和destination有任何的重叠,复制的结果都是未定义的。
原因也很简单:如下代码
int arr1[] = { 0,1,2,3,4,5,6,7,8,9 }; my_memcpy(arr1+2, arr1, 40);
给自己复制时,肯定时一位一位复制,把arr1[0]复制到arr+2(arr[2])位置时,arr1【2】的数值被覆盖为0,那么当我们继续复制时再取出arr[2]的值就是你之前已经复制过的了0,而不是原本的数值2,就不再是你想要复制的数据了。
4.
my_memcpy(arr2, arr1, 9);
这里我只复制前9个字节,可以发现打印出来了0,1,2.这是为什那么呢?
原因是:我们的vs编译器是小端存储(即,数据低位存到内存的高地址),
1,2,3在内存中的二进制存储为:
01 00 00 00|
02 00 00 00|
03 00 00 00 【一个00也就是一字节】
存储就9字节,正好把3 的关键位给复制进去了。
💭memmove函数
#include
一、memmove函数简介
void * memmove ( void * destination, const void * source, size_t num );
参数与memcpy一样
与memcpy函数区别是,它通常被用在源空间和目标空间出现重叠时
二、memmove函数的模拟
1.两种情况
memomove复制时,有两种情况
1.dest地址
2.dest地址>src地址: 从后到前(右到左)
2模拟实现
#define _CRT_SECURE_NO_WARNINGS 1 #include<stdio.h> #include<assert.h> void* my_memcpy(void* dest, void* src, size_t num) { void* ret = dest;//保存初始位置地址 assert(dest);//确保dest不为空 if (dest < src)//分两种情况 { while (num--)//情况一,从左到右复制 { *(char*)dest = *(char*)src; dest = (char*)dest + 1; src = (char*)src + 1; } } else { while (num--)情况二:从右到左复制 { *((char*)dest + num) = *((char*)src + num); //先强制转换成char型,再加上num个字节。 //就是指向src,dest的末尾元素 } } return ret; } int main() { int arr1[] = { 0,1,2,3,4,5,6,7,8,9 }; my_memcpy(arr1+5, arr1, 20); int i = 0; for (i = 0; i < 10; i++) { printf("%d\n", arr1[i]); } return 0; }
💭memcmp函数
#include
1.memecmp函数介绍
1.1定义:
int memcmp ( const void * ptr1, const void * ptr2, size_t num );
参数:ptr1和ptr2都指向内存块的指针。
num:要比较的字节数
返回值:
返回一个整数值,该值指示内存块内容之间的关系:
返回值 | 表明 |
小于0 | ptr2大(指向的第一个不相等字符块) |
0 | 两个内存块的内容相等 |
大于0 | ptr1大 |
1.2.功能:
将 ptr1 指向的内存块的前 num 字节数与 ptr2 指向的第一个字节数进行比较,
如果它们都匹配,则返回零,
如果不匹配,则返回一个不同于零的值,表示哪个值更大。 请注意,与 strcmp 不同,该函数在找到空字符后不会停止比较。
✨memset函数
#include
1.memset函数介绍
void * memset ( void * ptr, int value, size_t num );
参数: ptr;指向要填充的内存块的指针。
value:要设置的值。该值作为 int 传递,但该函数使用此值的无符号 char 转换填充内存块。
num:字节数
返回值:修改后的ptr
2.memset功能
3.memset使用
案例一:
#include<string.h> int main() { int arr[10] = { 0 }; memset(arr, 1, 20); return 0; }
它是将每一个字节都赋值成1;
案例二:
#include<string.h> int main() { char arr[10] = { "hellloni"}; memset(arr, 'x', 5); printf("%s", arr); return 0; }