2

独学でプログラミングを学ぼうと決めたとき、私は Java から始めました。また、単純な手続き型ソフトウェア (主に PHP) を作成することには慣れていますが、より複雑な操作ではオブジェクトに依存していることに最近気付きました。

私の最初の Java ゲームは、オブジェクトをインスタンス化することによって、ランダムな場所とランダムな速度で対戦相手を生成しました。これを C で手続き的に実装するという概念に戸惑っていますが (これについては実用的な知識がほとんどありません)、各対戦相手の変数に対して異なる配列を作成し、配列インデックスを疑似オブジェクト参照 '変数として使用することしか考えられませんでした。 '。

int size[50]; // opponent size
for (i = 0; i < 100; i++) {
    size[i] = random_number();
}

私のオブジェクト指向の心が見落としている簡単な解決策はありますか? それとも、偽のオブジェクトを作成する (または少なくとも同様のモデルを使用する) 必要があるという点で、オブジェクト指向の概念に本当に役立つ問題があるのでしょうか? 私は C コードで構造体をよく見かけますが、概念的にはクラスに似ていることは知っていますが、私が知っているのはそれだけです。ですから、このようなことが完全に非オブジェクト指向の考え方で可能かどうか疑問に思っています。インスタンス化に代わるものはありませんね。それはすべてメモリの割り当てにすぎないので、特定の C プログラムは、私がオブジェクトと見なす何らかの形式を使用して作成するしかありません。

そうでなければ、オブジェクト指向パラダイムを非難する C 純粋主義者を尊重できないからです。(私は決してオブジェクト指向の狂人ではありません。しかし、私の心はこの考えに非常に慣れてしまっており、慣れ親しんだものを提供しない別のレンズを通して物事を見るのは難しいです。)

ありがとう!

4

3 に答える 3

3

OO プログラマーとしての経験もある私は、手続き型プログラミングに慣れるのにも少し時間がかかりました。私にとって最大のことは、ポインターの操作に慣れることと、関数はオブジェクトによって管理されず、代わりに与えられた「オブジェクト」に作用することを覚えていることです。とにかく、このようなものは、あなたがやろうとしていることの手続き的なイメージを得るのを助けるためにあなたが探しているものかもしれないと思います.

struct creature {
    int speed;
    int size;
};

void init_creature(struct creature *c) {
    c->speed = random_number();
    c->size = random_number();
}

int main() {
    struct creature creatures[10];

    for (int i = 0; i < (sizeof(creatures)/sizeof(struct creature)); i++) {
        struct creature c = creatures[i];
        init_creature(&c);
    }
}
于 2013-01-09T21:36:14.877 に答える
1

高度なオブジェクト指向プログラミングの概念をすべて無視すると、型パラメーターによる継承またはポリモーフィズムとして、すべてが同じものになります。

C++ では、オブジェクトがあり、それらにアタッチされているメソッドを呼び出します。C では、構造体があり、これらの関数を引数で渡すことによってグローバル関数を呼び出します。

私が言いたいのは、本質的な oop パラダイムとは、概念的には、メソッドを通じて物事を実行できるオブジェクトを持つことであるということです。C でも同じ動作を得ることができますが、どのオブジェクトにも関連付けられていない関数があります。

したがって、基本的に C++ または Java では次のようになります。

class Point {
  private:
    int x, y;
  public:
    Point(int x, int y) : x(x), y(y) { }
    void draw() { ... }
};

純粋な C では、次のようになります。

struct Point {
  int x, y;
}

struct Point makePoint(int x int y) {
  struct Point p = {.x = x, .y = y};
  return p;
}

void drawPoint(struct Point p) {
  ..
}

しかし、両方の表現の意味論的な力は本質的に同じですが、構文は異なります (そしてその背後にある概念さえも)。もちろん、より強力な oop 機能を検討し始めると、すべてが変わります。

多くの状況では、オブジェクトを表現するためにこのようなすべての機能が必要なわけではありません。ゲーム用の複雑なエンジンを C で書くのはやり過ぎであると同時に、システムで動作する低レベル関数を Java で書くのはやり過ぎです。

于 2013-01-09T21:27:30.243 に答える
1

Astructは、おそらくここで探しているものです。

Astructには任意の数の名前付き変数 (クラスのプロパティなど) を含めることができますが、メソッドを含めることはできません (理論的には関数ポインターを介してメソッドを配置することはできますが、実際には思いどおりには機能しません)。

したがって、クリーチャーを C で表すと、次のような構造体になる可能性があります。

struct creature {
  int x_pos;
  int y_pos;
  int speed;
};

クリーチャー「オブジェクト」を宣言し、いくつかのプロパティを設定するには、次のようにします。

   void main() {
      struct creature mycreature;
      mycreature.x_pos = 1;
      mycreature.y_pos = 2;      
   }

構文は少し扱いに​​くいので、struct creature mycreature多くの場合、言う必要がなく、代わりに次のように言うことができるように構造体を作成します。typedefstruct creature mycreaturecreature mycreature

typedef struct _creature {
  int x_pos;
  int y_pos;
  int speed;
} creature;

構造体には他の構造体を含めることができるため、point構造体を作成して、代わりに位置変数に使用することもできます。

typedef struct _point {
  int x;
  int y;
} point;

typedef struct _creature {
  point location;
  int speed;
} creature;

void main() {
    creature mycreature;
    mycreature.location.x = 1;
    mycreature.location.y = 2;      
}

そして今、うまくいけば、物事はもう少し見慣れたものに見え始めます...

于 2013-01-09T21:32:31.023 に答える