22-03-2012, 10:31 AM
Je pense que j'utiliserais plein de colonnes pour décrire l'entité mais que la magie se ferait dans le code.
Pour cette affaire de cruche, voilà à quoi pourrait ressembler l'entrée dans la table items.
Elle aurait déjà une colonne name
Ensuite dans le code, tu peux étendre dynamiquement ton objet selon ses attributs.
Voilà, je pense qu'avec un code de ce genre, tu peux vraiment couvrir beaucoup de possibilité. Ça demande un peu de travail pour combiner les propriétés (genre un conteneur de liquide qui fait du bruit) mais ça se fait bien quand même.
Pour cette affaire de cruche, voilà à quoi pourrait ressembler l'entrée dans la table items.
Elle aurait déjà une colonne name
name
, une colonne material
(fer, bois, etc.), une colonne state
(solide, liquide, gazeux), des colonnes booléennes liquid_container
, weapon, noisy_container, cutting
, blunt
(contondant), des colonnes numériques volume
(pour déterminer ce qu'elle pourra contenir), weight
(pour déterminer les dégâts qu'il infligera), etc.Ensuite dans le code, tu peux étendre dynamiquement ton objet selon ses attributs.
# A l'utilisation :
item = Item.find(42)
rich_item = RichItem.build(item)
class RichItem
def self.build(item)
rich_item = RichItem.new(item)
rich_item.include(LiquidContainer) if item.container?
rich_item.include(Weapon) if item.weapon?
rich_item.include(NoisyContainer) if item.weapon?
rich_item
end
def initialize(item)
@item = item
end
end
class NoisyContainer
def content=(content)
@content = content
end
def content
@content
end
def noise
return 0 if @content.gas?
if (@content.volume * 2) < @item.volume
case @content.material
when 'wood' 50
when 'metal' 100
else raise(UnknownMaterial)
end
else
case @content.material
when 'wood' 20
when 'metal' 40
else raise(UnknownMaterial)
end
end
end
class UnknownMaterial < StandardError; end
end
class Weapon
def damage
if @item.blunt?
@item.weight * 2
elsif @item.cutting?
@item.weight
else
@item.weight / 2
end
end
end
class LiquidContainer
def content=(content)
@content = content
end
def content
@content
end
end
Voilà, je pense qu'avec un code de ce genre, tu peux vraiment couvrir beaucoup de possibilité. Ça demande un peu de travail pour combiner les propriétés (genre un conteneur de liquide qui fait du bruit) mais ça se fait bien quand même.