memcpy和memmove的區別以及內存重疊問題

memcpy和memmove的區別以及內存重疊問題

轉自:https://www.codecomeon.com/posts/89/

區別

memcpy()memmove() 都是C語言中的庫函數,在頭文件 string.h 中,作用是拷貝一定長度的內存的內容,原型分別如下:

void *memcpy(void *dst, const void *src, size_t count);
void *memmove(void *dst, const void *src, size_t count);

他們的作用是一樣的,唯一的區別是,當內存發生局部重疊的時候,memmove 保證拷貝的結果是正確的,memcpy 不保證拷貝的結果的正確。

函數原型

memcpy

  • 原型:

    void *memcpy(void *dest, const void *src, size_t n);
    
  • 描述:memcpy() 函數從 src 內存中拷貝 n 個字節到 dest 內存區域,但是源和目的的內存區域不能重疊。

  • 返回值:memcpy()函數返回指向dest的指針。

memmove

  • 原型:

    void *memmove(void *dest, const void *src, size_t n);
    
  • 描述:memmove() 函數從 src 內存中拷貝 n 個字節到 dest 內存區域,但是源和目的的內存可以重疊。

  • 返回值:memmove()函數返回一個指向dest的指針。

內存覆蓋情形

內存覆蓋的情形有以下兩種

在這里插入圖片描述

memcpy面對內存覆蓋的兩種情形

memcpy 函數實現

void* my_memcpy(void* dst, const void* src, size_t n)
{char *tmp = (char*)dst;char *s_src = (char*)src;while(n--) {*tmp++ = *s_src++;}return dst;
}

從實現中可以看出memcpy()是從內存左側一個字節一個字節地將src中的內容拷貝到dest的內存中,這種實現方式導致了對于圖中第二種內存重疊情形下,最后兩個字節的拷貝值明顯不是原先的值了,新的值是變成了src的最開始的2個字節了。

而對于第一種內存覆蓋情況,memcpy的這種拷貝方式是可以的。

memcpy針對第二種情形的改進——memmove

而memmove就是針對第二種內存覆蓋情形,對memcpy進行了改進,改進代碼如下:

void* my_memmove(void* dst, const void* src, size_t n)
{char* s_dst;char* s_src;s_dst = (char*)dst;s_src = (char*)src;if(s_dst>s_src && (s_src+n>s_dst)) {      //-------------------------第二種內存覆蓋的情形。s_dst = s_dst+n-1;s_src = s_src+n-1;while(n--) {*s_dst-- = *s_src--;}}else {while(n--) {*s_dst++ = *s_src++;}}return dst;
}

在第二種內存覆蓋的情形下面,memcpy會出錯,但是memmove是能正常工作的。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/532495.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/532495.shtml
英文地址,請注明出處:http://en.pswp.cn/news/532495.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

從頭搭建一個深度學習框架

從頭搭建一個深度學習框架 轉自:Build a Deep Learning Framework From Scratch 代碼:https://github.com/borgwang/tinynn 當前深度學習框架越來越成熟,對于使用者而言封裝程度越來越高,好處就是現在可以非常快速地將這些框架作為…

關于python import的sys.path路徑問題

關于python import的sys.path路徑問題 sys.path 先說一下 sys.path 這個變量,該變量需要導入 sys 官方庫方可使用,它是一個列表,是當前 python 文件 import 庫時會逐個搜索列表中的路徑。 初始化 sys.path 從這些位置初始化: …

python pdb調試基本命令整理

python pdb調試基本命令整理 使用簡介 啟動調試 侵入式 在 py 文件內部設置: import pdb; pdb.set_trace()程序會在運行到這一行時停下來,進入 pdb 交互。 非侵入式 在運行 py 腳本時: python -m pdb main.py程序會在一啟動時就進入 pdb 交…

Docker概念理解

Docker概念理解 本文非Docker命令大全,而是對Docker的概念、原理等作說明,適合有一定實操經驗后來加深理解。 轉自:docker從入門到實踐 Docker簡介 本章將帶領你進入 Docker 的世界。 什么是 Docker? 用它會帶來什么樣的好處&a…

Dockerfile詳解

Dockerfile詳解 轉自:https://yeasy.gitbook.io/docker_practice/ 使用Dockerfile定制鏡像 從剛才的 docker commit 的學習中,我們可以了解到,鏡像的定制實際上就是定制每一層所添加的配置、文件。如果我們可以把每一層修改、安裝、構建、操…

Dockerfile最佳實踐

Dockerfile最佳實踐 本文是原作者對 Docker 官方文檔中 Best practices for writing Dockerfiles 的理解與翻譯。 轉自:附錄四:Dockerfile 最佳實踐 一般性指南和建議 容器應該是短暫的 通過 Dockerfile 構建的鏡像所啟動的容器應該盡可能短暫&#xf…

Linux內存背后的那些神秘往事

Linux內存背后的那些神秘往事 作者:大白斯基(公眾號:后端研究所) 轉自:https://mp.weixin.qq.com/s/l_YdpyHht5Ayvrc7LFZNIA 前言 大家好,我的朋友們! CPU、IO、磁盤、內存可以說是影響計算機…

mmdeploy快速上手

mmdeploy快速上手 若要將使用 openmmlab 的框架(如mmdet、mmcls)等訓練的模型進行快速部署,同樣來自 openmmlab 的 mmdeploy 無疑是最合適的選擇,本文將簡單地完成一個 Faster RCNN 模型的部署。 配置 本文基于如下軟硬件配置&…

精簡CUDA教程——CUDA Driver API

精簡CUDA教程——CUDA Driver API tensorRT從零起步邁向高性能工業級部署(就業導向) 課程筆記,講師講的不錯,可以去看原視頻支持下。 Driver API概述 CUDA 的多級 API CUDA 的 API 有多級(下圖)&#xff…

CUDA編程入門極簡教程

CUDA編程入門極簡教程 轉自:CUDA編程入門極簡教程 作者:小小將 前言 2006年,NVIDIA公司發布了CUDA,CUDA是建立在NVIDIA的CPUs上的一個通用并行計算平臺和編程模型,基于CUDA編程可以利用GPUs的并行計算引擎來更加高效地…

精簡CUDA教程——CUDA Runtime API

精簡CUDA教程——CUDA Runtime API tensorRT從零起步邁向高性能工業級部署(就業導向) 課程筆記,講師講的不錯,可以去看原視頻支持下。 Runtime API 概述 環境 圖中可以看到,Runtime API 是基于 Driver API 之上開發的…

Python并發——concurrent.futures梳理

Python并發——concurrent.futures梳理 參考官方文檔: concurrent.futures — 啟動并行任務 Executor對象 class concurrent.funtures.Executor該抽象類是 ThreadPoolExecutor 和 ProcessPoolExecutor 的父類,提供異步執行調用方法。要通過它的子類調用…

TensorRT ONNX 基礎

TensorRT ONNX 基礎 tensorRT從零起步邁向高性能工業級部署(就業導向) 課程筆記,講師講的不錯,可以去看原視頻支持下。 概述 TensorRT 的核心在于對模型算子的優化(合并算子、利用當前 GPU 特性選擇特定的核函數等多種…

回文子串、回文子序列相關題目

回文子串、回文子序列相關題目 回文子串是要連續的,回文子序列可不是連續的。 516. 最長回文子序列 dp數組含義:dp[i][j]dp[i][j]dp[i][j] 表示子序列 s[i,j]s[i,j]s[i,j] 中的最長回文子序列的長度。 dp數組初始化:子序列長度為 1 時&am…

mmdetection tools工具梳理

mmdetection tools工具梳理 mmdetection 是一個非常好用的開源目標檢測框架,我們可以用它方便地訓練自己的目標檢測模型,mmdetection 項目倉庫提供許多實用的工具來實現幫助我們進行各種測試。本篇將梳理以下 mmdetection 項目倉庫 tools 目錄下的各種實…

TensorRT ONNX 基礎(續)

TensorRT ONNX 基礎(續) PyTorch正確導出ONNX 幾條推薦的原則,可以減少潛在的錯誤: 對于任何使用到 shape、size 返回值的參數時,例如 tensor.view(tensor.size(0), -1) 這類操作,避免直接使用 tensor.s…

frp實現內網穿透極簡教程

frp實現內網穿透極簡教程 本文是內網穿透極簡教程,為求簡潔,我們不介紹為什么內網穿透也不介紹其原理,這里假設各位讀者都已經明確的知道自己的目的,本文僅介紹如何安裝配置 frp 實現內網穿透。 簡單來說,內網穿透就…

圖像預處理之warpaffine與雙線性插值及其高性能實現

圖像預處理之warpaffine與雙線性插值及其高性能實現 視頻講解:https://www.bilibili.com/video/BV1ZU4y1A7EG 代碼Repo:https://github.com/shouxieai/tensorRT_Pro 本文為視頻講解的個人筆記。 warpaffine矩陣變換 對于坐標點的變換,我們通…

LeetCode-10 正則表達式匹配

LeetCode-10 正則表達式匹配 動態規劃 10. 正則表達式匹配 dp數組含義:dp[i][j]dp[i][j]dp[i][j] 表示 s[0:i?1]s[0:i-1]s[0:i?1] 能否被 p[0:j?1]p[0:j-1]p[0:j?1] 成功匹配。 狀態轉移方程 : 如果 s[i?1]p[j?1]s[i-1]p[j-1]s[i?1]p[j?1] …

shell if判斷和for循環常見寫法

shell if判斷和for循環常見寫法 轉自: Shell中for循環的幾個常用寫法 Shell中if 條件判斷總結 if常見寫法 一、if的基本語法: if [ command ];then符合該條件執行的語句 elif [ command ];then符合該條件執行的語句 else符合該條件執行的語句 fibash shell會按順序…