草庐IT

c++ - 内存碎片会减慢 New/Malloc 的速度吗?

coder 2024-02-10 原文

短背景:

我正在开发一个应该运行数月并使用动态分配的系统。

问题:

我听说内存碎片会减慢 newmalloc 运算符的速度,因为它们需要在我留下的“漏洞”之一中“找到”一个位置在内存中,而不是简单地在堆中“前进”。

我读过以下问题: What is memory fragmentation?

但是没有一个答案提到任何关于性能的事情,只是分配大内存块失败。

那么内存碎片是不是让new需要更多的时间来分配内存呢? 如果是,增加多少?我怎么知道 new 是否正在“艰难”地寻找堆上的内存?

我试图找到 GCC 用来在内存中找到要在内部分配的“洞”的数据结构/算法是什么。但找不到任何血统解释。

最佳答案

内存分配是特定于平台的,具体取决于平台。

我会说“是的,new 需要时间来分配内存。多少时间取决于许多因素,例如算法、碎片级别、处理器速度、优化等。

关于花费多少时间的最佳答案是分析和测量。编写一个简单的程序,对内存进行分段,然后测量分配内存的时间。

程序没有直接的方法来找出找到可用内存位置的难度。您可以读取一个时钟,分配内存,然后再次读取。另一个想法是设置一个计时器。

注意:在许多嵌入式系统中,动态内存分配是不受欢迎的。在关键系统中,碎片化可能是大敌。所以使用固定大小的数组。固定大小的内存分配(在编译时)消除了作为缺陷问题的碎片。

编辑 1:搜索
通常,内存分配需要调用一个函数。这样做的影响是处理器可能不得不重新加载其指令缓存或流水线,从而消耗额外的处理时间。也可能有额外的指令用于传递参数,例如最小尺寸。编译时的局部变量和分配通常不需要函数调用来分配。

除非分配算法是线性的(想想数组访问),否则将需要步骤来找到可用的槽。一些内存管理算法根据请求的大小使用不同的策略。例如,一些内存管理器可能有单独的池用于 64 位或更小的大小。

如果您将内存管理器视为具有 block 的链表,则该管理器将需要找到大于或等于请求大小的第一个 block 。如果 block 大于请求的大小,它可能会被拆分,然后将剩余的内存创建为一个新 block 并添加到列表中。

没有内存管理的标准算法。它们根据系统的需要而不同。具有受限(小)内存大小的平台的内存管理器将不同于那些具有大量内存的平台。关键系统的内存分配可能与非关键系统的不同。 C++ 标准不强制要求内存管理器的行为,只有一些要求。例如,允许内存管理器从硬盘驱动器或网络设备分配。

影响的重要性取决于内存分配算法。最佳途径是衡量目标平台上的性能。

关于c++ - 内存碎片会减慢 New/Malloc 的速度吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44767273/

有关c++ - 内存碎片会减慢 New/Malloc 的速度吗?的更多相关文章

  1. ruby-on-rails - Ruby net/ldap 模块中的内存泄漏 - 2

    作为我的Rails应用程序的一部分,我编写了一个小导入程序,它从我们的LDAP系统中吸取数据并将其塞入一个用户表中。不幸的是,与LDAP相关的代码在遍历我们的32K用户时泄漏了大量内存,我一直无法弄清楚如何解决这个问题。这个问题似乎在某种程度上与LDAP库有关,因为当我删除对LDAP内容的调用时,内存使用情况会很好地稳定下来。此外,不断增加的对象是Net::BER::BerIdentifiedString和Net::BER::BerIdentifiedArray,它们都是LDAP库的一部分。当我运行导入时,内存使用量最终达到超过1GB的峰值。如果问题存在,我需要找到一些方法来更正我的代

  2. ruby-on-rails - 如何优雅地重启 thin + nginx? - 2

    我的瘦服务器配置了nginx,我的ROR应用程序正在它们上运行。在我发布代码更新时运行thinrestart会给我的应用程序带来一些停机时间。我试图弄清楚如何优雅地重启正在运行的Thin实例,但找不到好的解决方案。有没有人能做到这一点? 最佳答案 #Restartjustthethinserverdescribedbythatconfigsudothin-C/etc/thin/mysite.ymlrestartNginx将继续运行并代理请求。如果您将Nginx设置为使用多个上游服务器,例如server{listen80;server

  3. ruby-on-rails - Enumerator.new 如何处理已通过的 block ? - 2

    我在理解Enumerator.new方法的工作原理时遇到了一些困难。假设文档中的示例:fib=Enumerator.newdo|y|a=b=1loopdoy[1,1,2,3,5,8,13,21,34,55]循环中断条件在哪里,它如何知道循环应该迭代多少次(因为它没有任何明确的中断条件并且看起来像无限循环)? 最佳答案 Enumerator使用Fibers在内部。您的示例等效于:require'fiber'fiber=Fiber.newdoa=b=1loopdoFiber.yieldaa,b=b,a+bendend10.times.m

  4. ruby-on-rails - Ruby 中的内存模型 - 2

    ruby如何管理内存。例如:如果我们在执行过程中采用C程序,则以下是内存模型。类似于这个ruby如何处理内存。C:__________________|||stack|||------------------||||------------------|||||Heap|||||__________________|||data|__________________|text|__________________Ruby:? 最佳答案 Ruby中没有“内存”这样的东西。Class#allocate分配一个对象并返回该对象。这就是程序

  5. ruby - 使用 `+=` 和 `send` 方法 - 2

    如何将send与+=一起使用?a=20;a.send"+=",10undefinedmethod`+='for20:Fixnuma=20;a+=10=>30 最佳答案 恐怕你不能。+=不是方法,而是语法糖。参见http://www.ruby-doc.org/docs/ProgrammingRuby/html/tut_expressions.html它说Incommonwithmanyotherlanguages,Rubyhasasyntacticshortcut:a=a+2maybewrittenasa+=2.你能做的最好的事情是:

  6. ruby - 如何计算 Liquid 中的变量 +1 - 2

    我对如何计算通过{%assignvar=0%}赋值的变量加一完全感到困惑。这应该是最简单的任务。到目前为止,这是我尝试过的:{%assignamount=0%}{%forvariantinproduct.variants%}{%assignamount=amount+1%}{%endfor%}Amount:{{amount}}结果总是0。也许我忽略了一些明显的东西。也许有更好的方法。我想要存档的只是获取运行的迭代次数。 最佳答案 因为{{incrementamount}}将输出您的变量值并且不会影响{%assign%}定义的变量,我

  7. 键删除后 ruby​​ 哈希内存泄漏 - 2

    你好,我无法成功如何在散列中删除key后释放内存。当我从哈希中删除键时,内存不会释放,也不会在手动调用GC.start后释放。当从Hash中删除键并且这些对象在某处泄漏时,这是预期的行为还是GC不释放内存?如何在Ruby中删除Hash中的键并在内存中取消分配它?例子:irb(main):001:0>`ps-orss=-p#{Process.pid}`.to_i=>4748irb(main):002:0>a={}=>{}irb(main):003:0>1000000.times{|i|a[i]="test#{i}"}=>1000000irb(main):004:0>`ps-orss=-p

  8. arrays - Ruby 数组 += vs 推送 - 2

    我有一个数组数组,想将元素附加到子数组。+=做我想做的,但我想了解为什么push不做。我期望的行为(并与+=一起工作):b=Array.new(3,[])b[0]+=["apple"]b[1]+=["orange"]b[2]+=["frog"]b=>[["苹果"],["橙子"],["Frog"]]通过推送,我将推送的元素附加到每个子数组(为什么?):a=Array.new(3,[])a[0].push("apple")a[1].push("orange")a[2].push("frog")a=>[[“苹果”、“橙子”、“Frog”]、[“苹果”、“橙子”、“Frog”]、[“苹果”、“

  9. ruby - 在 Ruby 中,为什么 Array.new(size, object) 创建一个由对同一对象的多个引用组成的数组? - 2

    如thisanswer中所述,Array.new(size,object)创建一个数组,其中size引用相同的object。hash=Hash.newa=Array.new(2,hash)a[0]['cat']='feline'a#=>[{"cat"=>"feline"},{"cat"=>"feline"}]a[1]['cat']='Felix'a#=>[{"cat"=>"Felix"},{"cat"=>"Felix"}]为什么Ruby会这样做,而不是对object进行dup或clone? 最佳答案 因为那是thedocumenta

  10. ruby-on-rails - HTTParty 的内存问题和下载大文件 - 2

    这会导致Ruby出现内存问题吗?我知道如果大小超过10KB,Open-URI会写入TempFile。但是HTTParty会在写入TempFile之前尝试将整个PDF保存到内存吗?src=Tempfile.new("file.pdf")src.binmodesrc.writeHTTParty.get("large_file.pdf").parsed_response 最佳答案 您可以使用Net::HTTP。参见thedocumentation(特别是标题为“流媒体响应机构”的部分)。这是文档中的示例:uri=URI('http://e

随机推荐