Ruby - quando usar variáveis ​​de instância vs parâmetros entre métodos?

8

Estou escrevendo vários métodos que chamam outros métodos.

Para passar as informações, tenho algumas opções:

  1. Passe as informações como parâmetros

  2. Defina variáveis ​​de instância para que outros métodos possam acessá-las

Quando devo escolher uma opção sobre a outra?

Parece que a primeira opção é boa, pois é muito específica sobre o que está sendo passado. a desvantagem parece ser que muitos valores estão sendo transmitidos.

O segundo método não requer a passagem de todos os valores, mas parece levar a muita magia, onde os métodos definem as variáveis ​​de instância 'em algum lugar'

Devo sempre ser muito explícito sobre ser passado para outros métodos da classe? Existem exceções para isso?

Michael Durrant
fonte
2
Muitas vezes tive a oportunidade de fazer alterações ou corrigir um bug em algum código que alguém escreveu usando a opção 2. Geralmente é uma bagunça emaranhada e as alterações se tornam muito demoradas. Mesmo depois de ter tudo resolvido, ainda é preciso muito esforço mental para fazer alterações, porque eu tenho que manter exatamente quando e onde as variáveis ​​são inicializadas ou atualizadas.
Aprendiz do Dr. Wily

Respostas:

12

Depende do papel dessas variáveis em relação a toda a classe .

Se sua classe é pequena e as informações que essas variáveis ​​transportam são relevantes para todas ou quase todas, então faz sentido tê-las como variáveis ​​de instância. Um objeto de conta bancária provavelmente precisa conhecer seu titular para a maioria das ações, portanto, faz sentido mantê-lo indefinidamente.

Se os dados são muito específicos para esse método e seus auxiliares, eles devem viajar como parâmetros. A data de uma transação não é tanto um recurso da conta como uma ação única executada nessa conta. (Se você tiver mais de um desses parâmetros, e eles tendem a ser passados ​​como unidade (por exemplo, data, hora do dia e fuso horário), também é aconselhável agrupá-los em um objeto auxiliar para manter o número de parâmetros baixa.)

Kilian Foth
fonte
14

Deixe-me citar você para deixar meu argumento claro:

Estou escrevendo várias funções que chamam outras funções. Para passar as informações, tenho duas opções:

  1. Passe as informações como argumentos.
  2. Use variáveis ​​globais.

Quando devo escolher uma opção sobre a outra?

É geralmente reconhecido que um estado não local é uma má ideia. Portanto, você geralmente deve passar as informações usando parâmetros, não através de variáveis ​​em um escopo comum. Isso se torna mais gerenciável se você agrupar informações relacionadas em objetos ou estruturas.

Passar muitos parâmetros é um cheiro de código e provavelmente pode ser refatorado para usar mais algumas classes. Suponha um caso patológico em que você esteja escrevendo um catálogo de endereços e tenha um método add_contact(surname, firstname, fullname, ...). Seria melhor grupo que em uma Nameclasse, mesmo para partes de um endereço: add_contact(name, address).

Se, no entanto, os parâmetros necessários para a sua função não estiverem completamente relacionados, pode ser que o seu método esteja tentando fazer muito e deve ser refatorado em partes menores.

Não creio que o uso de variáveis ​​de instância seja uma boa solução: é uma mutação desnecessária de estado e traz consigo todos os problemas de variáveis ​​globais, em uma escala menor. Dessa maneira, encontra-se um código de espaguete não debugável.

amon
fonte