我正在继续学习使用C ++的uni,我遇到了一些关于指针,const参数和类实现的所有基础知识的严重理解问题(与C ++相比,它在Java中非常容易)
我通常使用Java,所以C ++对我来说是一个新手。
这是我对“Person”类的简单标题:
#ifndef Person_h
#define Person_h
class Person
{
private:
char* name;
char* adress;
char* phone;
public:
Person();
Person(char const *name, char const *adress, char const *phone);
Person(const Person &other);
~Person();
void setName(char const *name);
char* getName() const;
void setAdress(char const *adress);
char* getAdress() const;
void setPhone(char const *phone);
char* getPhone() const;
};
#endif // !Person_h
这里问题就出现了。为什么我应该使用char指针而不是实际的char变量?我猜这是为了节省内存或提高性能的一些惯例?
这是我们教授编码的方式,并试图让我们理解指针的使用和const
等。
现在这是我的课程实现:
#include "Person.h"
//Person.h class implementation
Person::Person()
{
Person::name = new (char[64]);
Person::adress = new (char[64]);
Person::phone = new (char[64]);
}
Person::Person(const char *name, const char *adress , const char *phone)
{
Person::name = new (char[64]);
Person::adress = new (char[64]);
Person::phone = new (char[64]);
setName(name);
setAdress(adress);
setPhone(phone);
};
Person::Person(Person const &other)
{
Person::name = new (char[64]);
Person::adress = new (char[64]);
Person::phone = new (char[64]);
setName(other.getName);
setAdress(other.getAdress);
setPhone(other.getPhone);
};
Person::~Person()
{
delete [] name;
delete [] adress;
delete [] phone;
};
void Person::setName(const char *name)
{
this->name = name;
};
char* Person::getName() const
{
return name;
};
void Person::setAdress(char const *adress)
{
this->adress = adress;
};
char* Person::getAdress() const
{
return adress;
};
void Person::setPhone(char const *phone)
{
this->phone = phone;
};
char* Person::getPhone() const
{
return phone;
};
我们应该学习手动为元素分配内存并尝试处理整体内存管理。因此使用const参数作为setter函数。我想这是为了不改变元素参数?我很困惑,基本上......
我的IDE(MS VisualStudio 2015)将以下行标记为错误:
void Person::setName(const char *name)
{
this->name = name; //error
};
“'char char''类型的值不能分配给'char *'类型的实体
那么当我无法分配这些值时,为什么要使用const
?或者我怎么能“un-const”那些,而不是自己创建成员变量const
?
现在这件事对我来说只是一个很大的混乱。
编辑:我 为我的考试使用C字符串,这是为了理解指向我们教授的指针和内存管理。
答案 0 :(得分:3)
在外行人的术语中,当this->name = name;
为const且name
为非const时,this->name
不起作用的原因是因为您的函数承诺内容将name
视为只读,但通过将此指针指定给非const指针,您可以随意修改数据,从而违背您的承诺。
你的老师显然是在尝试用指针教你老式的C ++(基本上是面向对象的C),所以你应该不继续用字符串替换char指针。如果你这样做,你的老师可能会不高兴。
我们使用char*
代替char[]
的原因有很多。
一个原因是效率:如果可以传递char[]
,则需要将char[]
的全部内容复制到堆栈中。当您传递char*
时,您只是将指针复制到字符,这通常是一个机器字。
另一个原因是它实际上是不可能的。编译器没有内置的知识,即你的char[]
是零终止的,以便为它分配足够的堆栈空间并将其复制到堆栈中。该语言的创建者倾向于不将这种内置知识放在语言中。相反,他们决定将char[]
隐式转换为char*
,以便在您的函数中,您可以将其作为char*
接收并使用它执行您想要的操作。
另一个原因是如果你的char[]
有点太大,那么你的筹码就会溢出。
因此,出于所有这些原因,当我们想要传递比机器词更大(或更大)的类型的值时,我们不传递值本身,我们传递指针或对它们的引用。
答案 1 :(得分:2)
例如。
this->name = name;
有两个原因:首先是因为你试图将一种类型的变量分配给一个密切相关但仍然不同类型的变量。但这不是大问题。
最大的问题是你尝试重新分配原始指针this->name
(指向你已经分配的内存)和另一个指针(指向在其他地方)。
结果类似于
int a = 5;
int b = 10;
a = b;
然后想知道为什么a
不再等于5
。
这里有两个解决方案:第一个是继续使用指针然后复制字符串而不是分配指针。这是通过std::strcpy
函数完成的。
我建议的解决方案是停止使用字符串指针,而是使用标准C ++ std::string
类。然后你可以使用简单的赋值来复制字符串。它们还处理自己的内存,因此您不必担心内存泄漏,指针,释放无效指针或跟踪字符串的实际大小。
std::string
C ++类与Java String
类有一些相似之处,所以如果你来自Java背景,那么你应该很难调整。最大的不同是在使用std::string
的C ++中,您实际上可以直接将字符串与==
进行比较。
答案 2 :(得分:1)
在现代C ++中,您应该仍然了解内存管理,但为了便于阅读,异常安全和错误,您应该使用为您工作的容器,如std :: string。
const char * name表示你有一个指针,它指向一个内存部分,它本身就是const,这意味着这个内存部分内的数据不应该改变。
指针本身可以改变。
分配时
find . -name "*.jar" -exec cp {} $destination \;
您只是将指针this-> name指定给name的指针。但是,只有当指针属于可转换类型时,才能执行此操作。如果将this-> name的类型从char *更改为const char *类型,则编译器不应该抱怨。
但在你分配任何新东西之前,你应该清理内存,例如:删除[] this-> name