C++ strcat创建无限循环
我试图创建一个数组,每个对象在数组中应该有名称模型(i)其中是索引,我这样做,使他们将按降序排列的名称Model5,Model4。 ..我试图做到这一点使用char [],但由于某种原因在我的代码中使用for循环内的strcat使我卡住在一个无限循环,第二点,如果有人可以帮助转换索引的方式我可以连接名称并赋予构造函数。C++ strcat创建无限循环
#include <iostream>
#include <stdio.h>
#include <string>
using namespace std;
class CARRO {
public:
CARRO() {};
CARRO(char *modelo, unsigned ano);
char* getModelo();
unsigned getAno();
private:
char modelo[100];
unsigned ano;
};
void swap(int *p, int *q);
int partition(int *v, int start, int end);
int randomizedPartition(int *v, int start, int end);
void qsHelper(int *v, int start, int end);
void quickSort(int *v, int len);
void printList(CARRO *carros, unsigned len);
int main(int argc, char const *argv[]) {
CARRO carros[5];
unsigned len = sizeof(carros)/sizeof(CARRO);
for (int i = 0; i < len; ++i) {
char modelo[] = "Modelo";
char id[] = "I";
strcat(modelo, id);
unsigned ano = 1000 * (i+1);
carros[i] = CARRO(modelo, ano);
cout << carros[i].getModelo() << endl;
}
//printList(carros, len);
return 0;
}
CARRO::CARRO(char *modelo, unsigned ano) {
strcpy(this->modelo, modelo);
this->ano = ano;
}
如果我删除行:
strcat(modelo, id);
循环工作正常。我只是不明白为什么strcat会以某种方式产生一个无限循环。输出是这样的:(与线的strcat)
ModeloI
ModeloI
ModeloI
ModeloI
ModeloI
ModeloI
ModeloI
ModeloI
ModeloI
ModeloI
^CModeloI
环路工作正常。我只是不明白为什么strcat会以某种方式产生一个无限循环。输出是这样的:(用线strcat)
该循环不工作正常!你在摧毁记忆。让我们把一些箱子代表堆栈可能你的程序中可以看出(假设环路刚刚去各地1):
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| char modelo[7] | int i | unsigned len |
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| 'M' | 'o' | 'd' | 'e' | 'l' | 'o' | 0 | 1 | 0 | 0 | 0 | 5 | 0 | 0 | 0 |
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
所以,当你这样做:
strcat(modelo, id);
你最终会得到一个字节的缓冲区溢出。在我的具体的例子,这将覆盖变量i
的第一个字节,从而使你的循环无限期地持续下去:
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| char modelo[7] | int i |
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| 'M' | 'o' | 'd' | 'e' | 'l' | 'o' | 'I' | 0 | 0 | 0 | 0 |
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
^^^^^
Nul-terminator written
当然,我已经完全奠定了你的筹码是这样的一个例子。你的编译器可能不会像这样保持堆栈在一起。有可能是您的阵列后,额外的填充,它可能可能刚刚发生“工作”。变量i
可能被保存在寄存器中,永远不会在内存中,或者编译器可能已完全展开循环。你的架构可能是是big-endian(而不像我的例子中的little-endian)。
问题是,最终的行为是完全未定义的。即使您的计算机上获得一致的结果,我们也无法查看此代码并说出会发生什么。
因此,要解决这个问题,你可以简单地modelo
足够大的存储字符串"ModeloI"
包括终止,这意味着使它大到足以存储8个字节,而不是7:
char modelo[8] = "Modelo";
,那么你就已定义的行为,不管堆栈是否布局为低于或其他任何方式:
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| char modelo[8] | int i |
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| 'M' | 'o' | 'd' | 'e' | 'l' | 'o' | 'I' | 0 | 1 | 0 | 0 | 0 |
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
非常感谢你解释@paddy,我决定使用std :: string,所以现在问题已经解决了!但是非常感谢,现在我将在使用char []时知道。 –
如果您使用C++,你应该使用'的std :: string'和相关方法而不是C的'的strcat '与字符数组 –
'm odelo'只能创建到足以容纳您初始化的单词。如果使用'std :: strcat'使内容更长,则您正在写入数组边界之外导致未定义的行为。 – Galik
可能重复的[我只是无法找出strcat](http://*.com/questions/4707900/i-just-cant-figure-out-strcat) –