-4

I ma quite new to c++ and i got a small problem that is probably easy for others. I have a class A and a class B that extends class A. I have an object A, lets call it a1. I want to downcast a1 to a type B class using the syntax: "B b1=(B)a1;"

 class IAmortizabil
 {
 public:
     virtual double getAmortizare()=0;
 };



 class Utilaj : public IAmortizabil{
 protected:
     float valInventar;
     char codUtilaj[10];
     char *denUtilaj;
     int anIntrFunct;
     int durataNormata;

 public:

     Utilaj(){
         denUtilaj=NULL;
         valInventar=0;
         anIntrFunct=0;
         durataNormata=0;
     }

     Utilaj(char *codUtilaj, char *denUtilaj, float valInventar, int      anIntrFucnt, int durataNormata){
         strcpy(this->codUtilaj, codUtilaj);
         this->denUtilaj=new char[strlen(denUtilaj)+1];
         strcpy(this->denUtilaj, denUtilaj);
         this->valInventar=valInventar;
         this->anIntrFunct=anIntrFucnt;
         this->durataNormata=durataNormata;
     }

     Utilaj(Utilaj &u)
     {
         strcpy(codUtilaj, u.codUtilaj);
         denUtilaj = new char[strlen(u.denUtilaj) + 1];
         strcpy(denUtilaj, u.denUtilaj);
         valInventar = u.valInventar;
         anIntrFunct = u.anIntrFunct;
         durataNormata = u.durataNormata;
     }


     friend ostream &operator<<(ostream &iesire, Utilaj &u)
     {
         iesire << " cod utilaj " << u.codUtilaj << endl;
         iesire << "denumire utilaj " << u.denUtilaj << endl;
         iesire << "valoare inventar " << u.valInventar << endl;
         iesire << "an intrare in functiune " << u.anIntrFunct << endl;
         iesire << " durata normata " << u.durataNormata << endl;
         return iesire;
     }

     Utilaj operator=(Utilaj &u)
     {
         strcpy(codUtilaj, u.codUtilaj);
         if (denUtilaj != NULL)
             delete[]denUtilaj;
         denUtilaj = new char[strlen(u.denUtilaj) + 1];
         strcpy(denUtilaj, u.denUtilaj);
         valInventar = u.valInventar;
         anIntrFunct = u.anIntrFunct;
         durataNormata = u.durataNormata;
         return *this;
     }



     double getAmortizare()
     {
         cout << '\n';
         if (durataNormata != 0)
             return valInventar / durataNormata;
         else {
             cout << "Durata normata este 0=>eroare";
             return 0;
         }
     }


     ~Utilaj(){
         if(denUtilaj!=NULL){
             delete[]denUtilaj;
         }
     }
 };


 class Strung :public Utilaj
 {
 protected:
     int nrBucati;

 public:
     Strung() :Utilaj()
     {
         nrBucati = 0;
     }
     Strung(char *_codUtilaj, char *_denUtilaj, float _valInventar, int _an, int _durata, int _nrBucati) :Utilaj(_codUtilaj, _denUtilaj, _valInventar, _an, _durata)
     {
         nrBucati = _nrBucati;
     }

     Strung(Strung &s) :Utilaj(static_cast< Utilaj&>(s))
     {
         nrBucati = s.nrBucati;
     }

         };

EDIT: Addeted my classes maybe it helps. I know nothing here is "the way to do it" but my teacher wants them like this and it is no point in arguing with him.

Alexandru Sandu
  • 314
  • 2
  • 13
  • What is your question? – Robᵩ Feb 01 '18 at 22:41
  • You can't cast an object to another, you can only do it to pointer or reference. – llllllllll Feb 01 '18 at 22:42
  • The compiler should flag that as an error. Getting an answer to just this question won't help you in the long run. Please go through [a good textbook](https://stackoverflow.com/questions/388242/the-definitive-c-book-guide-and-list) to build a solid foundation. – R Sahu Feb 01 '18 at 22:42
  • What, like object slicing in reverse? How would that make sense? – melpomene Feb 01 '18 at 22:44
  • @liliscent And even then, it's only valid if the base class pointer actually points to an instance of the derived class. – Barmar Feb 01 '18 at 22:47
  • You can't convert a base class into a derived class because not all the bits are there. But if you have a derived class you can convert it to a base class (via slicing). With objects, casting is done with the pointer. For example if you have a base class pointer pointing to a derived object you can cast the base class pointer into a derived class pointer using dynamic_cast() – Jerry Jeremiah Feb 01 '18 at 22:47
  • Oh wait. I know what he is trying to do. He is trying to construct a derived class from a base class. You need a constructor that takes the base class object as a parameter for that to work. – Jerry Jeremiah Feb 01 '18 at 22:49
  • @Barmar Yes, just too many fundamental errors in OP's description. – llllllllll Feb 01 '18 at 22:51
  • Show us the definition of the classes. If the derived class has a constructor that takes a base class object you just need to `B b(a1);` And if it doesn't you will have to add one. – Jerry Jeremiah Feb 01 '18 at 22:52
  • @Barmar You can tell from his example that he isn't using pointers - I think he is trying to construct a B from an A. – Jerry Jeremiah Feb 01 '18 at 22:54
  • I think this will help: https://stackoverflow.com/questions/120876/what-are-the-rules-for-calling-the-superclass-constructor – Jerry Jeremiah Feb 01 '18 at 22:55
  • 1
    _" I want to downcast a1 to a type B"_ I suspect that you **don't** want to do that. What problem are you solving that makes you want to do that? – Drew Dormann Feb 01 '18 at 22:56
  • I have a main function from my teacher that needs to run certain lines of code. One of them is "B b1=(B)a1;". I am not new to programming, i programed java for almost 2 yreas, but i am new to C++... – Alexandru Sandu Feb 02 '18 at 07:59

1 Answers1

0

In C++ you can cast a pointer to a base type into a pointer to a derived type using dynamic_cast, assuming it pointed to the derived type in the first place.

class A
{
};

class B : public A
{
};

int main()
{
    A * a = new B();
    B * b = dynamic_cast<B*>(a);

    if( b == nullptr )
    {
        // Error - "a" was not a "B" object
    }

    return 0;
}

When you see (sometype)Object, in C++, that is a C-style cast, and is not the way to enlightenment. This is equivalent to a C++ reinterpret cast and can be quite dangerous. It certainly should not be used where a dynamic_cast is sufficient.

Also, in C++, when you have a polymorphic type, you must use a pointer. You would not cast an instance of an object, but rather, you would cast a pointer to the object.

Please Google both "dynamic_cast" and "reinterpret_cast" for a better understanding of both.

Christopher Pisz
  • 3,757
  • 4
  • 29
  • 65
  • I already managed to do it like u said, with a dynamic_cast but i was told by my teacher that it should be only with a C-style cast and got 0 points until i manage to do that... – Alexandru Sandu Feb 02 '18 at 08:08
  • @Alexandru If you are taking a class where you are learning C++, and your teacher told you to use a c-style cast, then your teacher is an idiot. Drop the class and go to the dean for a refund. Unfortunately, many college professors don't have the first clue about the differences between C and C++. Your choices in C++ are static_cast, dynamic_cast, reinterpret_cast, and const_cast. All with their own purpose. C-style cast is there for backwards compatibility with C, but you should always opt for one of the others in C++ as they are more safe. – Christopher Pisz Feb 02 '18 at 13:32
  • Thx, i read more about what you said, static_cast, dynamic and reinterpret and i had a little chitchat with m teacher giving him facts and relevant information and i mannage to convince him that what he was asking was wrong. – Alexandru Sandu Feb 05 '18 at 12:18
  • @AlexandruSandu Excellent! We've helped hundreds of future students in the process! Glad to hear! – Christopher Pisz Feb 09 '18 at 16:06