objektorientiertes c



  • ca. so:

    #include <iostream> 
    #include <vector> 
    #include <string>
    using namespace std; 
    
    enum type {
    	cat_animal,
    	dog_animal
    };
    
    class animal {
    private: 
        string name; 
    	type animal_type;
    
    public:
    	animal(string name_, type animal_type_): name(name_), 
    	                                         animal_type(animal_type_) {}
    	virtual string make_sound() = 0;
    }; 
    
    class cat : public animal {
    private:
    	int some_variabe2;
    
    public:
    	cat(string name_): animal(name_, cat_animal) {} 
    
    	virtual string make_sound() {
    		return "meow!";
    	}
    };
    
    class dog : public animal {
    private:
    	int some_variabe1;
    
    public:
    	dog(string name_): animal(name_, dog_animal) {} 
    
    	virtual string make_sound() {
    		return "bark!";
    	}
    };
    
    class animal_manager { 
    private:
        vector<animal*> vec; 
    
    public:
        void add_animal(animal *a) { 
    		vec.push_back(a); 
        }
    
        void print_animals() { 
    		for (int i = 0; i < vec.size(); i++) { 
            	cout << vec[i]->make_sound() << endl; 
        	}
        }
    }; 
    
    int main() { 
        animal_manager m; 
        m.add_animal(new cat("susi")); // i know we need to delete this object from the heap...
        m.add_animal(new dog("struppi")); // i know we need to delete this object from the heap...
        m.print_animals(); 
    
        return 0; 
    }
    


  • ich versuche gerade folgendes buch zu lesen und den c++ code auf c zu mappen: http://www.cs.rit.edu/~ats/books/ooc.pdf



  • Vererbung geht so, falls das die Frage war:

    struct dog
    {
    	animal base;
    	int some_variabe1;
    };
    

    Die Entsprechung von new ist in C nicht static , sondern malloc .



  • und wie kann ich dog in einem dynamischen array e.g.

    vector<animal*> vec;
    

    (achtung c++ code) speichern?



  • Ein Zeiger ist keine Referenz; wenn du das berücksichtigst, läuft doch alles wie gewünscht:

    #include <stdio.h>
    
    struct animal_vtable {
      const char* (*sound)();
    };
    
    struct animal {
      struct animal_vtable methods;
      const char* name;
    };
    
    const char* cat_sound()
    {
      return "meow!";
    }
    
    const char* dog_sound()
    {
      return "bark!";
    }
    
    struct animal_manager {
      struct animal vec[100];
      int i;
    };
    
    void add_animal(struct animal_manager *m, struct animal a)
    {
      m->vec[m->i++] = a;
    }
    
    void print_animals(struct animal_manager *m)
    {
      for (int i = 0; i < m->i; i++) {
        puts( m->vec[i].methods.sound() );
      }
    }
    
    // wie kann man das hier eleganter machen, und static vermeiden?
    struct animal new_cat(const char *name)
    {
      struct animal cat = { { &cat_sound }, name };
      return cat;
    }
    
    // wie kann man das hier eleganter machen, und static vermeiden?
    struct animal new_dog(const char *name)
    {
      struct animal dog = { { &dog_sound }, name };
      return dog;
    }
    
    int main()
    {
      struct animal_manager m = { 0 };
      add_animal(&m, new_cat("cat"));
      add_animal(&m, new_dog("dog"));
      print_animals(&m);
    
      return 0;
    }
    


  • dog *d = malloc(sizeof(*d));
    //.. vtable und andere Member initialisieren ..
    
    //beides ist möglich, wenn base am Anfang der Struktur steht:
    animal *a = &d->base;
    animal *b = (animal *)d;
    
    //darf man auch:
    dog *e = (dog *)a;
    




  • man kann sowas machen um inheritance zu simulieren. wie kann ich mir einen konstruktor / destructor bauen?

    #include <stdio.h>
    
    typedef struct {
      int x;
      int y;
    } point;
    
    typedef struct {
      point center;
      int radius;
    } circle;
    
    void init_point(point *p, int x, int y)
    {
      p->x = x;
      p->y = y;
    }
    
    void init_circle(circle *c, int x, int y, int r)
    {
      init_point((void *)c, x, y);
      c->radius = r;
    }
    
    int main(void) {
    	// your code goes here
    
    	circle c;
    
    	init_circle(&c, 1, 2, 3);
    
    	return 0;
    }
    


  • kann jemand mit ein besseres beispiel zeigen?

    #include <stdio.h>
    
    typedef struct {
      int x;
      int y;
    } point;
    
    typedef struct {
      point center;
      int radius;
    } circle;
    
    void init_point(point *p, int x, int y)
    {
      p->x = x;
      p->y = y;
    }
    
    void init_circle(circle *c, int x, int y, int r)
    {
      init_point((void *)c, x, y);
      c->radius = r;
    }
    
    point NewPoint() 
    {
      point p;
      p.x = 0;
      p.y = 0;
      return p;
    }
    
    void FreePoint(point *this_)
    {
    }
    
    circle NewCircle() 
    {
      circle ret;
      ret.center = NewPoint();
      ret.radius = 0;
      return ret;
    };
    
    void FreeCircle(circle *this_)
    {
    }
    
    int main(void) {
    	// your code goes here
    
    	circle c;
    	c = NewCircle();
    
    	init_circle(&c, 1, 2, 3);
    
    	FreeCircle(&c);
    
    	return 0;
    }
    


  • hi, ich habe nun ein basic example erstellt. wie kann ich den konstructor / destructor aus C++ nachbauen?

    #include <stdio.h>
    #include <math.h>
    
    struct shape;
    
    struct shape_vtable {
      float (*calc_area) (struct shape*);
    };
    
    struct shape {
    	int x;
    	int y;
    	struct shape_vtable *vtable;
    };
    
    struct shape NewShape() {
    	struct shape s;
    	s.x = 0;
    	s.y = 0;
    	return s;
    }
    
    void FreeShape(struct shape *this_) {
    }
    
    static void init_shape(struct shape *s, int x, int y) {
    	s->x = x;
    	s->y = y;
    }
    
    static float calc_area(struct shape *s) {
    	return s->vtable->calc_area(s);
    }
    
    struct circle {
    	struct shape super;
    	int radius;
    };
    
    struct circle NewCircle() {
    	struct circle ret;
    	ret.super = NewShape();
    	ret.radius = 0;
    	return ret;
    }
    
    void FreeCircle(struct circle *this_) {
    }
    
    static float circle_calc_area(struct shape *s) {
    	struct circle *c = (struct circle*)s;
    
    	return (c->radius * c->radius) / M_PI;
    }
    
    static struct shape_vtable circle_vtable = {
    	.calc_area = circle_calc_area,
    };
    
    static void init_circle(struct circle *c, int x, int y, int r) {
    	init_shape((void *)c, x, y);
    	c->super.vtable = &circle_vtable;
    	c->radius = r;
    }
    
    int main(void) {
    	// your code goes here
    
    	struct circle c;
    	c = NewCircle();
    
    	init_circle(&c, 1, 2, 3);
    
    	struct shape *s = (struct shape*)&c;
    	printf("%f", calc_area(s));
    
    	FreeCircle(&c);
    
    	return 0;
    }
    

Anmelden zum Antworten