在 C++ 中循环初始化和动态声明随机实体的多个变量
Posted
技术标签:
【中文标题】在 C++ 中循环初始化和动态声明随机实体的多个变量【英文标题】:Initialize and declare dynamically multiple variables of random entities in a loop in C++ 【发布时间】:2018-11-01 20:17:04 【问题描述】:这是我的代码:
#include <cstdlib>
#include <ctime>
#include <stdio.h>
#include <vector>
#define ENTITY(A) entity##A
#define ALM(A) alm##A
struct TEntity
private:
int sumx;
int sumy;
const char * rep;
int m_ix;
int m_iy;
public:
TEntity(int x, int y, int sum_x, int sum_y, const char * txt);
;
TEntity::TEntity(int x, int y, int sum_x, int sum_y, const char * txt)
m_ix = x;
m_iy = y;
sumx = sum_x;
sumy = sum_y;
rep = txt;
class IAlmacenable
private:
void * element;
public:
IAlmacenable(void * e);
IAlmacenable();
void * getValue();
;
IAlmacenable::IAlmacenable(void *e)
element = e;
IAlmacenable::IAlmacenable()
element = nullptr;
void * IAlmacenable::getValue()
return element;
class TList
private:
std::vector<IAlmacenable*> elementos;
int position;
public:
TList();
int Size();
int Push(IAlmacenable* psz);
;
TList::TList()
elementos = std::vector<IAlmacenable*>();
position = 0;
int TList::Size()
return elementos.size();
int TList::Push(IAlmacenable* psz)
int res = 0;
if (elementos.size() >= elementos.max_size())
res = -1;
else
elementos.push_back(psz);
return res;
int main()
srand(time(NULL));
TList *list = new TList();
//we can put entities in the list and the rest will be filled up to 5
int size = list->Size();
for(int i = size; i<5;i++)
const char c[] = (rand() % 2 ? 65 + rand() % 25 : 97 + rand() % 25), '\0';
TEntity ENTITY(i)(rand() % 10, rand() % 10, rand() % 5, rand() % 5, c);
IAlmacenable ALM(i)(&ENTITY(i));
list->Push(&ALM(i));
size++;
//do things like printing their value...
delete list;
return 0;
每次运行“TEntity ENTITY(i)”行时,我都需要创建一个新变量, 问题是它总是创建相同的变量,我认为这是因为它创建了变量 entityi,因此它覆盖了同一个变量,此外它生成的随机数似乎总是相同的数字,因为所有实体都具有相同的其所有参数中的值。 c 变量在 a-z, A-Z 之间创建一个 const char * 随机变量,我不放打印代码,因为它是不必要的,那我该怎么办?有没有办法动态创建值是随机的实体的变量?
编辑 这是修复的新代码(宏已被删除,因为它们不是必需的,并且已经包含了能够执行它的必要代码)但仍然存在相同的问题,即它们是使用相同的参数生成的(因为它们是仍然是同一个变量):
#include <cstdlib>
#include <ctime>
#include <stdio.h>
#include <vector>
#include <conio.h>
#include <windows.h>
struct TEntity
private:
int sumx;
int sumy;
const char * rep;
int m_ix;
int m_iy;
public:
TEntity(int x, int y, int sum_x, int sum_y, const char * txt);
void movimiento();
void pinta();
;
TEntity::TEntity(int x, int y, int sum_x, int sum_y, const char * txt)
m_ix = x;
m_iy = y;
sumx = sum_x;
sumy = sum_y;
rep = txt;
void TEntity::movimiento()
m_ix += sumx;
m_iy += sumy;
void TEntity::pinta()
gotoxy(static_cast<short int>(m_ix), static_cast<short int>(m_iy));
printf("%s", rep);
void gotoxy(short int x, short int y)
COORD pos = x, y;
HANDLE output = GetStdHandle(STD_OUTPUT_HANDLE);
SetConsoleCursorPosition(output, pos);
void clear()
system("cls");
class IAlmacenable
private:
void * element;
public:
IAlmacenable(void * e);
IAlmacenable();
void * getValue();
;
IAlmacenable::IAlmacenable(void *e)
element = e;
IAlmacenable::IAlmacenable()
element = nullptr;
void * IAlmacenable::getValue()
return element;
class TList
private:
std::vector<IAlmacenable*> elementos;
int position;
public:
TList();
int Size();
int Push(IAlmacenable* psz);
IAlmacenable* First();
IAlmacenable* Next();
;
TList::TList()
elementos = std::vector<IAlmacenable*>();
position = 0;
int TList::Size()
return elementos.size();
int TList::Push(IAlmacenable* psz)
int res = 0;
if (elementos.size() >= elementos.max_size())
res = -1;
else
elementos.push_back(psz);
return res;
IAlmacenable* TList::First()
IAlmacenable* res;
if (elementos.empty())
res = nullptr;
else
res = elementos.front();
position = 1;
return res;
IAlmacenable* TList::Next()
IAlmacenable* res;
if (elementos.empty())
res = nullptr;
else
int pos = position;
int size = elementos.size();
if (pos < size)
res = elementos.at(position);
position++;
else
res = this->First();
return res;
int main()
srand(time(NULL));
TList *list = new TList();
//we can put entities in the list and the rest will be filled up to 5
int size = list->Size();
for(int i = size; i<5;i++)
const char c[] = (rand() % 2 ? 65 + rand() % 25 : 97 + rand() % 25), '\0';
TEntity *entity = new TEntity(rand() % 10, rand() % 10, rand() % 5, rand() % 5, c);
IAlmacenable *alm = new IAlmacenable(entity);
list->Push(alm);
size++;
while(true)
clear();
for (int i = 0; i < size; i++)
reinterpret_cast<TEntity *>(list->Next()->getValue())->pinta();
reinterpret_cast<TEntity *>(list->Next()->getValue())->movimiento();
Sleep(2000);
delete list;
return 0;
【问题讨论】:
宏在运行前很久就扩展了 你几乎可以说它们发生在编译时间之前(如果你觉得预处理器实际上不是编译器的一部分) 问题是它总是创建相同的变量,我认为这是因为它创建了变量 entityi,因此它覆盖了同一个变量,此外它生成的随机数似乎总是相同的数字,因为所有实体在其所有参数中都具有相同的值 无论如何你都有更大的问题。对象的范围是循环迭代,因此(a)它可以在每次迭代中具有相同的名称,并且(b)您正在存储指向死亡事物的指针。 " 问题是它总是创建相同的变量" 不它没有,它每次都是一个新变量,即使它们重用相同的内存地址。 【参考方案1】:这里有些混乱。
几点:
-
您已经知道,该宏不适合用途;你只是每次都创建一个变量名
entityi
;
没关系!无论如何,该对象仅在循环迭代期间存在; C++ 不允许您同时创建多个具有相同名称的对象。事实上,你可以摆脱整个宏的东西,只需调用对象entity
;
现在已经不碍事了,您会得到重复的结果,因为您要存储一个指向该局部变量的每次迭代的指针——在每次迭代中,它都是一个指向已销毁对象的悬空指针。不要存储悬空指针!
您可以:
动态分配要添加到列表中的对象,或 存储实际对象而不是指向对象的指针。无论哪种方式,局部作用域名称都是无关紧要的,当然也不需要为每次循环迭代重复更改。
【讨论】:
但我需要他们的指针,因为我会将它们放在一个包装器中(IAlmacenable) @YamikaIzumi 然后您需要动态分配它们,以便您可以精细控制它们的生命周期。你用哪本书来学习 C++? 我是在大学学的,不知道你说的动态分配是什么意思?我必须在 for 中创建它并将其输入到辅助列表中,以便可以查阅并输入到我的 TList 中? @YamikaIzumi Noooo。当您使用new
时,您正在“动态分配”。我再次问您使用的是哪本 C++ 书?它应该解释所有这些基础知识。
C++ 编程语言。贝雅内·斯特劳斯特鲁普。我已经编辑了我的问题,消除了宏并添加了执行所需的代码,此外,我尝试在 TEntity 的创建行中创建新的,但是当我没有创建任何东西时以上是关于在 C++ 中循环初始化和动态声明随机实体的多个变量的主要内容,如果未能解决你的问题,请参考以下文章
C++《8. C++11 做了什么让成员的初始化变简单了?》- 知识点目录