3
respostas

Erro "private method to_csv"

Quando executo o meu código, ocorre um erro no método exporta_csv, mais precisamente na chamada que está no método "puts livro.to_csv".

Segue o erro:

livro.rb:45:in `block in exporta_csv': undefined method `to_csv' for nil:NilClass (NoMethodError)
Did you mean?  to_c
               to_s        
from livro.rb:44:in `each'
from livro.rb:44:in `exporta_csv'
from livro.rb:82:in `<main>'

Classe Livro:

class Livro
    attr_reader :titulo, :ano_lancamento, :possui_reimpressao
    attr_accessor :preco

    def initialize(titulo, preco, ano_lancamento, possui_reimpressao)
        @titulo = titulo
        @ano_lancamento = ano_lancamento
        @possui_reimpressao = possui_reimpressao
        @preco = calcula_preco(preco)
    end

    def possui_reimpressao?
        @possui_reimpressao
    end

    private

    def calcula_preco(base)
        if @ano_lancamento < 2006
            if @possui_reimpressao
                base * 0.9
            else
                base * 0.95
            end
        elsif @ano_lancamento <= 2010
            base * 0.96
        else
            base
        end
    end

    def to_csv
        "#{@titulo},#{@ano_lancamento},#{@preco}"
    end
end

Classe Estoque:

class Estoque

    def initialize
        @livros = []
    end

    def exporta_csv
        @livros.each do |livro|
            puts livro.to_csv
        end
    end

    def mais_baratos_que(valor)
        @livros.select do |livro|
            livro.preco <= valor
        end
    end

    def total
        @livros.size
    end

    def adiciona(livro)
        @livros << livro if livro
    end
end

Chamadas e execuções:

def livro_para_newsletter(livro)
    if livro.ano_lancamento < 1999
        puts "Newsletter/Liquidacao"
        puts livro.titulo
        puts livro.preco
        puts livro.possui_reimpressao?
    end
end

algoritmos = Livro.new("Algoritmos", 100, 1998, true)
arquitetura = Livro.new("Introdução a Arquitetura e Design de Software", 70, 2011, true)

estoque = Estoque.new
estoque.adiciona algoritmos 
estoque.adiciona arquitetura
estoque.adiciona Livro.new("The Pragmatic Programmer", 100, 1999, true)
estoque.adiciona Livro.new("Programming Ruby", 100, 2004, true)

estoque.exporta_csv

baratos = estoque.mais_baratos_que 80
baratos.each do |livro|
    puts livro.titulo
end

Obrigado desde já.

3 respostas

Ele indica que você está tentando chamar o método em um referência que está nula... Precisa dar uma debugada no seu código e entender pq a variável que deveria apontar para um Livro está nula.

Alberto, não lembro exatamente onde mexi, mas hoje o código estava gerando um outro erro, indicando que o método to_csv estava privado.

Verifiquei que na ordem em que estava o código, ele havia sido definido abaixo do método calcula_preco que está marcado como privado.

Só estou com essa dúvida: a partir do momento que defino um método como private, os outros métodos abaixo dele serão entendidos como privado?

Obrigado.

Você está com toda razão, é assim que funciona :).