user1543042
user1543042

Reputation: 3440

Vector of Inherited Class

When I am trying to make an overarching vector of shapes and in this place different shapes like "octahedron", "cuboid", "sphere", ...

I was trying to do something similar to this http://www.cplusplus.com/forum/general/2710/ but the lines 121 - 136

if (shape_type == 0) {
  sphere->set_shape(Coordinates, Properties, mode);
  ShapeVector.push_back(sphere);
}
else if (shape_type == 2) {
  ellipsoid->set_shape(Coordinates, Properties, mode);
  ShapeVector.push_back(ellipsoid);
}
else if (shape_type == 3) {
  cuboid->set_shape(Coordinates, Properties, mode);
  ShapeVector.push_back(cuboid);
}
else if (shape_type == 4) {
  octahedron->set_shape(Coordinates, Properties, mode);
  ShapeVector.push_back(octahedron);
}

but I get the error

main.cpp:122:54: warning: ‘sphere’ may be used uninitialized in this function [-Wuninitialized] main.cpp:126:57: warning: ‘ellipsoid’ may be used uninitialized in this function [-Wuninitialized] main.cpp:130:54: warning: ‘cuboid’ may be used uninitialized in this function [-Wuninitialized] main.cpp:134:58: warning: ‘octahedron’ may be used uninitialized in this function [-Wuninitialized]

Please if anyone had a suggestion I would appreciate it. In case you want it the full file is below.

#include <iostream>
#include <cstring>
#include <fstream>
#include <vector>
#include <sstream>
#include <cstdio>
#include "ShapeContainer.H"

using namespace std;

int main () {

  //    Declaration of Variables    //
  vector <double> input;
  vector <double> BoundingBoxDimension; // Will be in the form X,Y,Z,dX,dY,dZ

  //    Note: shape_type follows same convention as Stat3D 
  //        0 = Sphere
  //        1 = Cylinder
  //        2 = Ellipsoid
  //        3 = Cuboid
  //        4 = Octahedron
  unsigned int shape_type;
  unsigned int mode;
  vector <double> Coordinates; //   Coordinates of Center of each shape 

  //    Properties of the shape
  //        For:
  //            Spheres:    r
  //            Cylinders:  R,h,v1,v2,v3
  //            Ellipsoid:  a,b,c,a1,a2,a3,b1,b2,b3 ... will calculate c1,c2,c3
  //            Cuboid:     a,b,c,a1,a2,a3,b1,b2,b3 ... will calculate c1,c2,c3
  //            Octahedron: a,b,c,a1,a2,a3,b1,b2,b3 ... will calculate c1,c2,c3
  vector <double> Properties;
  double item;
  string line;

    vector <Shape*> ShapeVector;
  ShapeContainer SC;

  //////    These are some default options used in development
  //////        feel free to delete them when finished
  string inputFileName = "../Cuboid.in";
  string Stat3DFileName = inputFileName;
  string T3DFileName = inputFileName;

  Stat3DFileName.insert(Stat3DFileName.rfind("."), "_Rewrite");
  T3DFileName.insert(T3DFileName.rfind("."), "_T3D"    );

  //    Set some options    //
  bool ReWriteStat3D = true;

  //    Set Shapes  //
  //        (if need to add a new shape, add shape here)
  Sphere* sphere;
  Ellipsoid* ellipsoid;
  Cuboid* cuboid;
  Octahedron* octahedron;

  //    Open File   //
  ifstream inputFile (inputFileName.c_str());

  if ( !inputFile.is_open() ) {
    cout << "Can not find specified input file,\n  " << inputFileName.c_str() << "\nplease check the file and try again.\n";
    return 0;
  }

  //    Read File Contents  //

  //    Gets Bounding Box Dimensions from First Line of File    //
  getline(inputFile, line);
  istringstream iss(line); //   Get a line of data corresponds to 1 item.
  while (iss >> item) {BoundingBoxDimension.push_back(item);}; //   Parses the data from the line
  if (BoundingBoxDimension.size() == 0) {
    cout << "Bounding box does not follow recognized format.\nPlease have the first line be either\ndx dy dz\nor\nx y z dx dy dz\n";
    return 0;
  }
  else if (BoundingBoxDimension.size() == 3) {BoundingBoxDimension.insert(BoundingBoxDimension.begin(),3,0);};
  SC.set_BoundingBox(BoundingBoxDimension);
  //    Takes number of particles and total number
  //        of rows and does not record them
  getline(inputFile, line);
  getline(inputFile, line);

  //    Get Data for each shape starting at line
  while (getline(inputFile, line)) {
    istringstream iss(line); // Get a line of data corresponds to 1 item.
    input.resize(0,0);

    while (iss >> item) {input.push_back(item); }; //   Parses the data from the line

    //  Set shape type  //
    shape_type=input[0]; // What type of shape is it?

    //  Set Mode (Stat3D) / Property (T3D) //
    mode=input[1]; //   What material is it (mode Stat3D/ Property T3D)

    //  Set coordinates //
    Coordinates.push_back(input[2]); // x
    Coordinates.push_back(input[3]); // y
    Coordinates.push_back(input[4]); // z

    //  Puts sizing and orientation into Properties
    for (unsigned int i = 5; i < input.size(); i++) {Properties.push_back(input[i]);};

    //  Calculates the c1,c2,c3 of shapes defined that way
    if (Properties.size() == 9)
      {
      double length;
      length = sqrt(pow(Properties[3],2)+pow(Properties[4],2)+pow(Properties[5],2));
      for (unsigned int PC = 3; PC <= 5; PC++) {Properties[PC] = Properties[PC] / length;}

      length = sqrt(pow(Properties[6],2)+pow(Properties[7],2)+pow(Properties[8],2));
      for (unsigned int PC = 6; PC <= 8; PC++) {Properties[PC] = Properties[PC] / length;}

        Properties.push_back(Properties[4]*Properties[8]-Properties[6]*Properties[7]);
        Properties.push_back(Properties[5]*Properties[6]-Properties[3]*Properties[8]);
        Properties.push_back(Properties[3]*Properties[7]-Properties[4]*Properties[6]);
      };

    if (shape_type == 0) {
      sphere->set_shape(Coordinates, Properties, mode);
      ShapeVector.push_back(sphere);
    }
    else if (shape_type == 2) {
      ellipsoid->set_shape(Coordinates, Properties, mode);
      ShapeVector.push_back(ellipsoid);
    }
    else if (shape_type == 3) {
      cuboid->set_shape(Coordinates, Properties, mode);
      ShapeVector.push_back(cuboid);
    }
    else if (shape_type == 4) {
      octahedron->set_shape(Coordinates, Properties, mode);
      ShapeVector.push_back(octahedron);
    }
    Coordinates.clear();
    Properties.clear();
  }

  inputFile.close(); // Closes Input File

/*
  //    Prints out the shapes
  ofstream T3DFile (T3DFileName.c_str());
  PrintT3D(T3DFile, SC);
  T3DFile.close();

  //    If option ReWriteStat3D is set to true, a new file for Stat3D is created 
  if (ReWriteStat3D == true) {
    ofstream Stat3DFile (Stat3DFileName.c_str());
    PrintStat3D(Stat3DFile, SC);
    Stat3DFile.close();
  };
*/
  return 0;
}

Upvotes: 1

Views: 223

Answers (1)

Luchian Grigore
Luchian Grigore

Reputation: 258678

Sphere* sphere; declares an un-initialized Sphere pointer. The compiler is warning you that you're doing it wrong - you should initialize it to something meaningful:

Sphere* sphere = new Sphere;

or, better yet:

vector <std::shared_ptr<Shape> > ShapeVector;
//...
std::shared_ptr<Shape> sphere(new Sphere);
//...

This way you have the same semantics, and are also using RAII correctly. If you however use the first version, you'll need to delete the memory manually, which isn't required when using smart pointers.

Whatever you do, don't forget that Shape::~Shape() should be virtual

Upvotes: 3

Related Questions