オブジェクト指向におけるFizzBuzz問題

オブジェクト指向は苦手なので練習してみる

【問題】
class Program {
public static void Main() {
Animal animal;
animal = new Dog();
animal.Sound();
animal.SetCount(3);
animal.Sound();
animal = new Cat();
animal.Sound();
}
}
上記のプログラムを実行した結果が
わん
わんわんわん
にゃー
となるように Animal, Cat, Dog を実装しなさい。

http://blogs.wankuma.com/episteme/archive/2007/11/08/106927.aspx

Ruby

まずは普通のオブジェクト指向言語Rubyで書いてみる。

class Animal
  def initialize() @voice,@count='',1 end
  def sound() puts @voice*@count end
  def setcount(n) @count=n end
end

class Dog < Animal
  def initialize() @voice,@count='わん',1 end
end

class Cat < Animal
  def initialize() @voice,@count='にゃー',1 end
end

animal=Dog.new;
animal.sound
animal.setcount(3);
animal.sound
animal=Cat.new;
animal.sound

JavaScript

ついでにJavaScriptでも書いてみる。

<html><body><script>
Animal={
  count:1,
  setcount:function(n){this.count=n;},
  sound:function(){
    for(var i=0,s='';i<this.count;i++) s+=this.voice;
    document.write(s+'<br>');
  }
}

function Dog(){this.voice='わん';}
Dog.prototype=Animal;

function Cat(){this.voice='にゃー';}
Cat.prototype=Animal;

animal=new Dog();
animal.sound();
animal.setcount(3);
animal.sound();
animal=new Cat();
animal.sound();
</script></body></html>

答え合わせ

だめだった。以下のようなことは考えてなかった。

Animal animal = new Animal();
って"できてしまう"のはどぉよ? てートコでしょうか。

導出クラスが基底クラスのメンバ'Nakigoe'をいぢくる
のはあんまキモチのいいもんじゃありませんですな。

http://blogs.wankuma.com/episteme/archive/2007/11/08/106927.aspx

勉強のためこの辺のことを考慮した修正版を作ってみる(後半の呼び出し部分は同じなので省略)

module Animal
  def sound() puts voice*count end
  def setcount(n) count=n end
end

class Dog
  include Animal
  def initialize() @voice,@count='わん',1 end
  attr_reader :voice
  attr_accessor :count
end

class Cat
  include Animal
  def initialize() @voice,@count='にゃー',1 end
  attr_reader :voice
  attr_accessor :count
end

rubyで抽象クラスを作るのはmoduleでいいのかな?
countの書き込みメソッド(count=)が動かないのはなんでだろ?