C ++派生的类构造函数

时间:2018-10-17 23:55:09

标签: c++ inheritance constructor

我正在学习C ++继承,但是我有一些问题。 我正在将Zinjal IDE与GNU c ++编译器一起使用。

这是代码:

class String {
protected:
    char str[MAX_STR_SIZE];
public:
    String(char str_init[])
    {
        strcpy(str, str_init);
    }
};

class PString : String
{ 
    public:
    PString(char str_init[]) 
    {
        if (strlen(str_init) > MAX_STR_SIZE)
            strncpy(str, str_init, MAX_STR_SIZE-1);
        else
            String(str_init); 
    }
};

好吧,这只是在创建我自己的“字符串”类。但是:有什么问题?字符串可能会变得太大。因此,当我的“ String”类的构造函数用字符串代替“ MAX_STR_SIZE”(定义为80个字符)调用时,程序将因数组溢出(> 80个字符)而崩溃。 所以我想创建一个名为“ PString”的“子”或“派生”类,它可以处理溢出。 如您所见,PString子类的构造函数将检查字符串是否大于MAX_STR_SIZE。如果它大于char数组可以处理的字符,则将MAX_STR_SIZE截断该字符串,从而避免溢出。如果小于MAX_STR_SIZE,则调用Parent类构造函数。 但是,g ++无法告诉我“没有匹配的函数调用'String :: String()'。

我知道这是一个la脚的错误,但我只是在学习

谢谢。

3 个答案:

答案 0 :(得分:1)

您不能只是突然调用构造函数。您只能在特定的地方调用构造函数,而这不是其中之一。

编译器看到String(str_init);并认为这是一个函数调用,但是您没有匹配的函数-因此出错。

根据下面的评论,这里有一个微妙之处。错误消息是“没有匹配的函数调用'String :: String()”。在名为String的类中,名为String的方法将成为构造函数。因此,行String(str_init);不是函数调用,它正在尝试使用不存在的默认构造函数来创建String项目。

答案 1 :(得分:-1)

您要尝试执行的操作不需要这套复杂性。通常,strncpy将正确处理这两种情况。但是,为了教育起见,这里进行一些分析

1。在PString的构造函数中,调用String的构造,并要求将str_intit转换为str。因此,您将导致您想要避免的相同内存损坏。您缺少String()构造函数。我建议为String创建默认的构造函数,并从PString中删除您使用的那个。

 String() {str[0] = 0;}
 ..
 PString(char str_init[])
 {

2。您的情况可以作如下修改:

if (strlen(str_init) > MAX_STR_SIZE) {
  strncpy(str, str_init, MAX_STR_SIZE-1);
  str[MAXLEN-1] = 0; // strncpy will not add '0' in this case. you need to do it yourself
}
else
  strcpy(str, str_init);

在上述if子句中,您使用str n cpy是否在'else'之后可以使用简单的strcpy。因此,它看起来像这样:

#include <cstring>
#define MAX_STR_SIZE 80

class String {
protected:
  char str[MAX_STR_SIZE];
public:
  String(char *str_init)
  {
    strcpy(str, str_init);
  }
  String() {
   str[0] = 0;
  }
};

class PString : String
{ 
public:
  PString(char str_init[])
  {
    if (strlen(str_init) > MAX_STR_SIZE) {
      strncpy(str, str_init, MAX_STR_SIZE-1);
      str[MAX_STR_SIZE-1] = 0;
    }
    else
      strcpy(str, str_init);
  }
};

答案 2 :(得分:-2)

2个错误。 首先,您需要通过该类的初始化程序列表调用基本构造函数,如本answer所述。

第二,在调用时需要为您的班级分配一些对象

String(str_init); 

以下代码在我的计算机上编译。

#include <cstring>
#define MAX_STR_SIZE 20
class String {
protected:
    char str[MAX_STR_SIZE];
public:
    String(char str_init[])
    {
        std::strcpy(str, str_init);
    }
};

class PString : String
{ 
    public:
    PString(char str_init[]) : String(str_init) 
    {
        if (strlen(str_init) > MAX_STR_SIZE)
            strncpy(str, str_init, MAX_STR_SIZE-1);
        else
            String s = String(str_init); 
            String s2(str_init);
    int i = 0;
    i++;
    }
};