10 votes

Accéder à une variable déclarée dans un autre fichier rb

Ceci est une question de débutant sur l'inclusion de fichiers .rb.

Je voudrais avoir accès à un tableau déclaré dans un autre fichier rb. Mon programme principal ressemble à ceci :

#!/usr/bin/env ruby
load 'price.rb'
[...]
max_price = price[az][type] * 2
[...]

et voici le price.rb :

price = {'us-east-1' => {'t1.micro' => 0.02, 'm1.small' => 0.08, 'c1.medium' => 0.165, 'm1.large' => 0.320 },
'us-west-1' => {'t1.micro' => 0.02, 'm1.small' => 0.08, 'c1.medium' => 0.165, 'm1.large' => 0.320 },
'eu-west-1' => {'t1.micro' => 0.02, 'm1.small' => 0.085, 'c1.medium' => 0.186, 'm1.large' => 0.340 }
}

Lorsque j'exécute le script principal, j'obtiens cette erreur :

Erreur : variable locale ou méthode `price' non définie pour main:Object

Qu'en pensez-vous ?

11voto

tadman Points 70178

La meilleure façon d'exporter des données d'un fichier et de les utiliser dans un autre est soit une classe, soit un module.

Un exemple est :

# price.rb
module InstancePrices
  PRICES = {
    'us-east-1' => {'t1.micro' => 0.02, ... },
    ...
  }
end

Dans un autre fichier, vous pouvez require ceci. Utiliser load est incorrect.

require 'price'

InstancePrices::PRICES['us-east-1']

Vous pouvez même raccourcir ceci en utilisant include :

require 'price'

include InstancePrices
PRICES['us-east-1']

Ce que vous avez fait est un peu difficile à utiliser. Un design orienté objet approprié encapsulerait ces données dans une sorte de classe, puis fournirait une interface à cela. Exposer vos données directement va à l'encontre de ces principes.

Par exemple, vous voudriez une méthode InstancePrices.price_for('t1.micro', 'us-east-1') qui retournerait le tarif approprié. En séparant la structure interne utilisée pour stocker les données de l'interface, vous évitez de créer de grandes dépendances au sein de votre application.

3voto

akluth Points 3304

Déclarer la variable à l'intérieur d'une classe minuscule et simple serait la solution la plus propre à mon avis.

3voto

Une citation d'un forum Ruby:

Gardez à l'esprit que l'utilisation de load garde les variables locales dans leur portée dans le fichier.

Cela signifie que vous pouvez utiliser la variable price seulement si elle n'est pas locale; un exemple avec une variable d'instance:

@price = {'us-east-1' => {'t1.micro' => 0.02, 'm1.small' => 0.08, 'c1.medium' => 0.165, 'm1.large' => 0.320 }, 'us-west-1' => {'t1.micro' => 0.02, 'm1.small' => 0.08, 'c1.medium' => 0.165, 'm1.large' => 0.320 }, 'eu-west-1' => {'t1.micro' => 0.02, 'm1.small' => 0.085, 'c1.medium' => 0.186, 'm1.large' => 0.340 } }

3voto

msangel Points 1716

Vous ne pouvez pas accéder à une variable depuis un autre fichier, mais vous pouvez accéder à une fonction depuis un autre fichier:

file1.rb

# en cas de script, vous pouvez utiliser des variables 'globales' (avec $) 
# car elles ont une visibilité de portée à l'ensemble de ce fichier 
$foo = 'bar'

def getFoo
    $foo
end

file2.rb

require_relative 'file1.rb'
foo = getFoo
# ...

2voto

junky Points 671

Je pense oublier les fichiers.

Pensez aux classes et aux méthodes.

Quelques options sont:

  • mettre ces méthodes et variables à l'intérieur d'une classe dans un fichier .rb.

  • mettre les variables et la méthode dans des fichiers différents et les inclure

Vous devrez réfléchir aux classes et aux méthodes et aux inclusions et aux extensions pour avoir une solution logique.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X