与SO上的很多问题和答案相关,我已经了解到最好引用其生命周期被管理为驻留在自动存储而不是堆栈中的对象.
此外,动态分配的对象不应该被称为驻留在堆上,而应该被称为动态存储.
我知道有自动,动态和静态存储,但从来没有真正理解自动堆栈和动态堆之间的区别.为什么前者更受青睐?
我不是在询问堆栈/堆的含义或内存管理的工作原理.我问为什么术语自动/动态存储优于术语堆栈/堆.
可能重复:
为什么你想要在堆而不是堆栈上分配内存?
Test2 *t2 = new Test2();
t2->test();
Test2 t3;
t3.test();
Run Code Online (Sandbox Code Playgroud)
为什么我要创建Test2类型的指针对象?为什么不做Test2的非指针版本?我为什么要做指针对象?
在这里找到答案:
我有一项任务要求我们实现双向链表类.出于某种原因,他们将节点定义struct如下:
struct node {
node *next;
node *prev;
T *o;
};
Run Code Online (Sandbox Code Playgroud)
在我看来,如果struct成员'data'不是指针,那么编写类会容易得多.不用说我无法改变它所以我将不得不解决它.我尝试实现将元素添加到列表开头的方法,如下所示:
template <typename T>
void Dlist<T>::insertFront(T *o) {
node *np = new node;
T val = *o;
np->o = &val;
np->prev = NULL;
np->next = first;
if (!isEmpty()) {
first->prev = np;
} else {
last = np;
}
first = np;
}
Run Code Online (Sandbox Code Playgroud)
在使用ddd进行调试的时候,我意识到第一次插入数字时一切正常,但第二次绕过一切都搞砸了,因为一旦你将'val'设置为新元素,它就会"覆盖"第一个自记忆以来使用了val的地址.我尝试做其他事情,而不是只是让'val'变量执行以下操作:
T *valp = new T;
T val;
valp = &val;
val = *o;
np->o = valp
Run Code Online (Sandbox Code Playgroud)
这似乎也没有用.我认为这是因为它只是一个更复杂的形式,我上面做的只是额外的内存泄漏:)
任何正确方向的想法/指针都会很棒.
更正:
我搞砸了指针地址的概念和指针指向的地址,因此修改了以下代码.现在它打印出我想要的东西,变量a,c,i,j,k,p在堆栈上,变量b,d在堆上.静态和全局变量在另一个段上.非常感谢大家!
嗯,我知道这两个概念已经深入讨论了......但是我仍然对以下代码有疑问:
#include <iostream>
using namespace std;
class A {
};
int N = 10;
void f(int p) {
int j = 1;
float k = 2.0;
A c;
A* d = new A();
static int l = 23;
static int m = 24;
cout << "&c: " << &c << endl;
cout << "&d: " << d << endl;
cout << "&j: " << &j << endl;
cout << "&k: " << &k << endl;
cout << "&l: …Run Code Online (Sandbox Code Playgroud) 在静态数组上使用malloc(除了NULL返回失败)有什么好处?以下程序将占用我所有的ram并且只有在取消注释循环时才开始填充交换.它没有崩溃.
...
#include <stdio.h>
unsigned int bigint[ 1u << 29 - 1 ];
unsigned char bigchar[ 1u << 31 - 1 ];
int main (int argc, char **argv) {
int i;
/* for (i = 0; i < 1u << 29 - 1; i++) bigint[i] = i; */
/* for (i = 0; i < 1u << 31 - 1; i++) bigchar[i] = i & 0xFF; */
getchar();
return 0;
}
Run Code Online (Sandbox Code Playgroud)
...
经过一些反复试验后,我发现上面是我的32位Intel机器上允许使用GCC 4.3的最大静态阵列.这是标准限制,编译器限制还是机器限制?显然我可以拥有我想要的那么多.这将是段错误,但只有当我要求(并尝试使用)时,malloc才会给我更多.
有没有办法确定静态数组是否实际分配并且可以安全使用?
编辑:我感兴趣的是为什么malloc用于管理堆而不是让虚拟内存系统处理它.显然,我可以将一个数组的大小调整到我认为我需要的大小的很多倍,并且虚拟内存系统只会保留ram所需的内容.如果我从未写过例如这些巨大数组的结束(或开头)那么程序就不会使用物理内存.此外,如果我可以写入每个位置,那么malloc除了在堆中递增指针或在同一进程中搜索先前的分配外,还做了什么呢?
编者注: 如果int是32位,则1 << …
我真的不明白什么时候应该在堆上分配内存,什么时候应该在堆栈上分配内存。我真正知道的是,在堆栈上分配速度更快,但由于堆栈较小,我不应该使用它来分配大型数据结构;在决定在哪里分配内存时我还应该考虑哪些其他因素?编辑:我应该在哪里分配实例变量?
我想知道我们什么时候应该使用unique_ptr(or boost::scope_ptr) 而不是本地对象。
我能想到的有两种可能的情况:
对象很大,超过了线程的堆栈大小。但在这种情况下,您始终可以增加线程的大小。
多态性。例如unique_ptr<C> p; if ... p.reset(new C1); else p.reset(new C2);。但我不确定我们什么时候需要这个。如果这p是一个函数的参数,我们可以简单地说:if ... foo(new C1); else foo(new C2);
还有其他情况我们应该使用unique_ptr而不是本地对象吗?
可能重复
在C++中正确的堆栈和堆使用?
我开始从Java背景学习C++,一个很大的区别是我不再被迫:
就像Java中的情况一样.但我很困惑何时应该做什么 - 你能建议吗?
目前我很想开始做Java风格的一切
Thing *thing = new Thing();
thing->whatever();
// etc etc
Run Code Online (Sandbox Code Playgroud) 我想从文件中按行收集的数据创建一个结构.每一行都需要一个新的结构,并在while循环中访问这些行.在C#中,我通过创建匿名结构并将它们添加到结构列表来实现此目的.C++似乎不允许匿名结构.我尝试使用递增变量命名它们,但是这不起作用,因为变量名称是字面意义的 - 无论如何,我宁愿不要被迫使用这种方法,因为我讨厌无关名称的想法.我想我可以通过一个独特的属性命名结构,但显然,我宁愿使用属性作为...财产.此外,如果它们不一定都是独一无二的呢?
有人可以提出建议或解释一些我错过的东西吗?
谢谢!
在c#中(psuedo:
public static List<Referral> Referrals = new List<Referral>();
//in loop:
var NewReferral = new Referral(referringURL.Trim(), referringWords.Trim().ToLower() , 1);
if ( NewReferral.URL == referringURL.Trim() ) {Referrals.Add(NewReferral);
Run Code Online (Sandbox Code Playgroud)
在c ++中:
list<CollectedData> AllData;
ifstream myFile("test_data.txt");
if (myFile.fail()) {cout << "Error opening file"; return 0;}
else
{
cout << "File opened... \n";
while( getline(myFile, line) ) {
struct CollectedData;
//add property values
//add struct to struct list
}
}
Run Code Online (Sandbox Code Playgroud)
(请详细了解它们何时自动删除,它可能没有帮助,但我想知道.谢谢!)
我什么时候应该使用指针而不是?什么是更好的方式?我必须删除程序结束时指针的cat对象吗?
例:
cat piki;
piki.miao();
cat *piki2 = new cat();
piki2->miao();
Run Code Online (Sandbox Code Playgroud) 可能重复:
点(.)运算符和C++中的 - >有什么区别?
使用点符号和指针方式有什么区别?
使用或不使用指针实例化对象.
实例化w/oa指针=然后使用点表示法
实例化w/a指针=然后使用 - >
两者有什么不同?何时以及为什么要使用另一个?
如何为类类型重载new运算符,以便它在堆栈而不是堆上分配内存(基本上这样用户之后就不必调用delete).
这样的事情怎么样:
class A{
private:
A(int i):
this->i(i);
{}
A a;
int i;
public:
void* operator new(size_t sz){
a(12);
}
};
Run Code Online (Sandbox Code Playgroud)
以上解决方案是否有效?