此问题旨在用作此常见问题解答的规范副本:
我在一个函数内动态分配数据,一切运行良好,但只在分配发生的函数内部.当我尝试在函数外部使用相同的数据时,我会遇到崩溃或其他意外的程序行为.
这是一个MCVE:
#include <stdlib.h>
#include <stdio.h>
void create_array (int* data, int size)
{
data = malloc(sizeof(*data) * size);
for(int i=0; i<size; i++)
{
data[i] = i;
}
print_array(data, size);
}
void print_array (int* data, int size)
{
for(int i=0; i<size; i++)
{
printf("%d ", data[i]);
}
printf("\n");
}
int main (void)
{
int* data;
const int size = 5;
create_array(data, size);
print_array(data, size); // crash here
free(data);
}
Run Code Online (Sandbox Code Playgroud)
每当print_array从create_array函数内部调用时,我得到预期的输出0 1 2 3 4 …
c malloc parameter-passing pass-by-value dynamic-memory-allocation
我并不真正理解C中的一些基本内容,比如动态分配数组数组.我知道你可以这样做:
int **m;
Run Code Online (Sandbox Code Playgroud)
为了声明一个二维数组(随后将使用一些*alloc函数分配).也可以通过这样做"轻松"访问它*(*(m + line) + column).但是我应该如何为该数组中的元素赋值?使用gcc时,以下语句m[line][column] = 12;因分段错误而失败.
任何文章/文档将不胜感激.:-)
出于好奇,以下是合法的吗?
X* p = static_cast<X*>(operator new[](3 * sizeof(X)));
new(p + 0) X();
new(p + 1) X();
new(p + 2) X();
delete[] p; // Am I allowed to use delete[] here? Or is it undefined behavior?
Run Code Online (Sandbox Code Playgroud)
同理:
X* q = new X[3]();
(q + 2)->~X();
(q + 1)->~X();
(q + 0)->~X();
operator delete[](q);
Run Code Online (Sandbox Code Playgroud) c++ arrays initialization placement-new dynamic-memory-allocation
我正在阅读Scott Meyers的Effective C++ 55,并从第49项中得到一个问题:
当operator new无法满足内存请求时,它会重复调用new-handler函数,直到找到足够的内存.
精心设计的newhandler函数必须执行以下操作之一:
当new无法分配内存时,就意味着没有足够的内存,问题是newhandler如何以及从哪里分配更多内存?
你能解释所有这些步骤吗?
在许多教程中,关于动态内存的第一个代码示例开始于:
int * pointer;
pointer = new int; // version 1
//OR
pointer = new int [20]; // version 2
Run Code Online (Sandbox Code Playgroud)
他们总是着手解释第二个版本是如何工作的,但完全避免谈论第一个版本.
我想知道的是,pointer = new int创造了什么?我该怎么办?这是什么意思?每个教程都没有失败,将避免完全讨论第一个版本.所有我发现的(通过搞乱)都是这样的:
#include <iostream>
using namespace std;
int main()
{
int * pointer;
pointer = new int;
pointer[2] = 1932; // pointer [2] exists? and i can assign to it?!
cout << pointer[2] << endl; // ... and access it successfully?!
};
Run Code Online (Sandbox Code Playgroud)
我可以下标的事实pointer告诉我到目前为止pointer = new int隐含地创建了一个数组.但如果是这样,那么它的大小是多少?
如果有人能帮我解决这一切,我将不胜感激......
在C++中,如果要动态分配数组,可以执行以下操作:
int *p;
p = new int[i]; // i is some number
Run Code Online (Sandbox Code Playgroud)
但是,要删除数组,你要...
delete[] p;
Run Code Online (Sandbox Code Playgroud)
为什么不呢delete p[]?这与它最初创建的方式不会更加对称吗?是什么原因(如果有的话)为什么语言是这样设计的?
c++ language-design dynamic-memory-allocation delete-operator
我期待了解GNU/Linux系统中动态内存管理如何在低级别工作(也就是说,ptmalloc如何工作).
当然,我已经阅读了代码,但我有很多疑问.我或多或少地了解数据结构,但我有很多信息泄漏!
我的问题是,如果有人知道任何资源详细解释实施.例如,我读过诸如"通过打破它来理解堆"或"Malloc Malleficarum"系列和后期系列等论文.他们做得很好,但是,当然,他们更专注于利用,而不是解释许多实施细节.
如果你不知道任何资源,这里有一些我的问题.
什么是竞技场?在来自heap_info结构的变量ar_ptr的代码中,有一条评论说"这个堆的竞技场",所以一个竞技场不能是一个堆(就像所说的那样).
为什么在heap_info结构中没有下一个指针并且有一个prev指针?是因为main_arena?什么是main_arena?
每个heap_info结构都可以有多个竞技场(指向不同的malloc_state结构)?
什么时候创建新闻竞技场和什么代码处理它?我已经读过,当请求存储数据的竞技场被锁定时(因为进程或进程线程正在使用它),我创建了新的竞技场,并且我还读到每个进程线程都有不同的竞技场.这里重要的是你知道什么代码处理这些情况.
我也不明白人们什么时候说所有的记忆操作都来自顶级大块或者大块头.你知道我在哪里可以找到这段代码吗?
顺便说一下,我不想深入了解互斥锁细节.
我正在审查glibc 2.12.1中的ptmalloc实现.我想做一些关于一切的整体结构的图表,所以我需要了解这些事情!
谢谢.
我的具体问题是,在C++中实现单例类时,以下两个代码之间在性能,方面问题或其他方面存在实质性差异:
class singleton
{
// ...
static singleton& getInstance()
{
// allocating on heap
static singleton* pInstance = new singleton();
return *pInstance;
}
// ...
};
Run Code Online (Sandbox Code Playgroud)
还有这个:
class singleton
{
// ...
static singleton& getInstance()
{
// using static variable
static singleton instance;
return instance;
}
// ...
};
Run Code Online (Sandbox Code Playgroud)
(请注意,基于堆的实现中的解除引用不应该影响性能,因为AFAIK没有为解除引用生成额外的机器代码.似乎只需要语法来区分指针.)
更新:
我有一些有趣的答案和评论,我试着在这里总结一下.(建议有兴趣的人阅读详细的答案.):
static singleton& getInstance() {
static std::auto_ptr<singleton> instance (new singleton());
return *instance.get();
}
Run Code Online (Sandbox Code Playgroud)
使用动态分配的单例比静态单例变量"更懒惰",如后一种情况,单例对象所需的内存(始终?)在进程启动时保留(作为加载程序所需的整个内存的一部分)并且只调用单例构造函数被推迟到getInstance()调用时.这可能sizeof(singleton)很重要.
两者都是C++ 11中的线程安全的.但是对于早期版本的C++,它是特定于实现的. …
我在讲座中被教过,free()两次拨打指针真是非常糟糕.我知道NULL在释放它之后立即设置指针是一种很好的做法.
但是,我仍然没有听到任何解释为什么会这样.根据我的理解,方式malloc()有效,它应该在技术上跟踪它已经分配的指针并让你使用.那么为什么它不知道它接收到的指针是否free()已被释放?
当你打电话free()给以前已经被释放的位置时,我很乐意理解,内部会发生什么.
这合法吗?ptr它可以在被释放后分配给它吗?
int * ptr = (int*) malloc(sizeof(int));
free(ptr);
ptr = (int *) malloc(sizeof(int));
Run Code Online (Sandbox Code Playgroud)