2017-05-05 246 views
-2

我一直在教自己的C++从一本书。我陷入了四个步骤中的第二个。这第二部分,虽然我被告知我必须“使这个类通用,使形状的边可能是整数或浮动。”C++ Missing Template参数问题

到目前为止,这是一个非常简单的程序。有三个脚本。有main.cpp,shape.cpp和shape.h。

该程序采用字符串中的对象名称,长度为浮点数,重要的是边。我有一个构造函数将对象,边和长度放在一起来创建一个通用形状对象,我将在后面进行升级。

但现在是使其更通用,所以我认为这与模板命令有关。这可能是非常容易的,我很抱歉浪费你的时间。看来我必须改变线形形状(对象,objectSides,objectLength);但我不知道在哪种方式,因为其他示例似乎表明你在头和其他类中做。

main.cpp | 35 | error:缺少'形状'之前的模板参数| main.cpp | 38 |错误:'shape'未在此范围内声明|

的main.cpp

#include <iostream> 
#include "shape.h" 

using namespace std; 

int main() { 
//Setting variables to 0; 
    string object; 
    int objectSides = 0; 
    int objectSidesTemp = 0; 
    float objectLength = 0; 
    float objectLengthTemp = 0; 

//Taking input for user on object being made. 
    cout << "Object to make: "; 
    cin >> object; 

//Input for sides being inputted. If below 3, asks user again for a valid number. 
//Assigns in temp number until within bounds, then assigns to objectSides. 
    while (objectSidesTemp < 3){ 
    cout << "How many sides (Must be 3 or greater): "; 
    cin >> objectSidesTemp; 
    } 
    objectSides = objectSidesTemp; 

//Input for length being inputted. If 0 or below, asks user again for a valid number. 
//Assigns in temp number until within bounds, then assigns to objectLength. 
    while (objectLengthTemp <= 0){ 
    cout << "Length of sides: "; 
    cin >> objectLengthTemp; 
    } 
    objectLength = objectLengthTemp; 

//Creates object of Shape called shape. Inputs the object name, sides, and length. 
    Shape shape(object, objectSides, objectLength); 

//Displays object specifics. 
    shape.display(); 
} 

shape.h

#ifndef SHAPE_H 
#define SHAPE_H 

#include <string> 

using namespace std; 

template <class T> 
class Shape { 

public: 
    Shape(string, T, float); 
    void setObject(string); //Used to ensure constructor works 
// virtual void setObject(string) = 0; 
//Used setObject as virtual function since constructor uses it to 
//Make the object using the setObject function. 
    string getObject(); 
    T getSides(); 
    bool setSides(T); 
    float getLength(); 
    void setLength (float); 

    float getPerimeter(int, float); 
    float getArea (int, float); 

    void display(); 
private: 
    string object; 
    T sides; 
    float length; 
}; 

#endif 

shape.cpp

#include <iostream> 
#include <string> 
#include "shape.h" 

using namespace std; 

//Constructor of Shape. Inpunts shape, sides, and length. 
    Shape::Shape (string shapes, int sides, float length){ 
     setObject(shapes); 
     setSides(sides); 
     setLength(length); 
    } //End of Shape constructor 

//Method to request the amount of sides, returns as an int 
//Because there are no lesser than full sides. 
    template <class T> 
    T Shape::getSides() { 
     return sides; 
    } //End of function getSides 

//Method to set the amount of sides. Return method is a bool. 
//If sideNumber is 0 or less in sides, returns a false. 
//If sideNumber is greater than 1, returns true. 
//Would recommend setting minimum of sides to 3 or greater, 
//as anything less is either a shape, a dot, or nothing. 
    bool Shape::setSides(int sideNumber) { 
     if (sides > 0){ 
      sides = sideNumber; 
      return true; 
     } 
     else { 
      return false; 
     } 
    } //End of function setSides 

//Returns string tied to the shape's object. 
//Future in 2D suggests triangle, rectangle, or square. 
//Implimented currently as any string. 
    string Shape::getObject(){ 
     return object; 
    } //End of function getObject 

//Sets input of the string to the variable object. 
    void Shape::setObject(string obj){ 
     object = obj; 
    } //End of function setObject 

//Retrieves float of length, as length can be numbers with decimals. 
    float Shape::getLength(){ 
     return length; 
    } //End of function getLength 

//Sets length of the object. Uses void because it doesn't need to return anything. 
    void Shape::setLength(float objectLength){ 
     length = objectLength; 
    } //End of function setLength 

//Sets area usings 3 sides or 4 sides else returns a 0. 
//Returning as float because objectLength is used as a float. 
    float Shape::getArea (int objectSides, float objectLength) { 
     if (objectSides == 3){ 
      return (objectSides * objectLength)/2; 
     } 
     if (objectSides == 4){ 
      return (objectLength * objectLength); 
     } 
//  return objectSides * objectLength; 
     return 0; 
    } //End of function getArea 

//Float return of that parimeter. Multipling sides by length to achieve. 
    float Shape::getPerimeter (int objectSides, float objectLength){ 
     return objectSides * objectLength; 
    } //End of function getParimeter. 

//Display function shows the Shape's varaibles. 
//Uses getParimeter and getArea commands to generate further information of the shape. 
    void Shape::display() { 
     cout << "Object: " << object << endl; 
     cout << "Sides: " << sides << endl; 
     cout << "Length: " << length << endl; 
     cout << "Perimeter: " << getPerimeter(sides, length) << endl; 
     cout << "Area: " << getArea(sides, length) << endl; 
    } //End of function display. 
+0

请不要变身你的问题到另外一个,如果它存在无效答案。如果维托里奥的答案解决了您问到的第一个问题,请将其标记为正确的答案。如果您有后续问题,请提出一个完全不同的问题。但不要这样做,因为你的后续问题[将是重复的](http://stackoverflow.com/questions/495021/why-can-templates-only-be-implemented-in-the-header - 文件) - 所有的信息在那里。我正在回滚你的编辑。 – Quentin

+1

@Greg是的它 - 你现在正在得到一个新的,完全不相关的错误。你的第一个错误是语法错误,这是一个链接错误。请阅读我上面链接的问答以解决这个问题。不要担心,我明白了为什么你会认为他们是相关的,但他们真的不是:) – Quentin

回答

1

您定义Shape为采取单一模板参数一个类模板T

template <class T> 
class Shape { /* ... */ }; 

因此,你需要明确指定T实例Shape时:

Shape<int> shape(object, objectSides, objectLength); 
// ^^^ 
+3

整个cpp文件也是错误的,你不能在头文件和cpp文件中拆分模板类。 – NathanOliver

+0

@NathanOliver:正确。我甚至懒得去看剩下的代码,太多无关的内容。 –

+0

当你对一个类进行模板化时,你应该将定义和声明放在头文件中,如第一条注释中所指出的那样。想想为什么这是必需的。这不是任意的,并且会理解模板。 – doug