试图找出Ruby在一些基本类上抛出错误的原因&;方法

试图找出Ruby在一些基本类上抛出错误的原因&;方法,ruby,csv,Ruby,Csv,我已经从Ruby Pickaxe的书中写了一些代码,我正在努力让它工作。 (在《实用程序员指南》第62页左右) **编辑:更多关于这本书的信息:(C)2009,Ruby 1.9版 鉴于此错误信息,我不太确定如何识别出哪里出了问题。我很感激任何帮助我理解这里出了什么问题 一个人如何知道识别和解决什么? 我想知道Ruby的CSV功能是否真的这么简单——不需要运行gem/bundle安装 我真的希望能够运行test_code.rb文件,但我无法找出这个错误 谢谢你抽出时间, 帕特里克 注意:所有这些

我已经从Ruby Pickaxe的书中写了一些代码,我正在努力让它工作。 (在《实用程序员指南》第62页左右) **编辑:更多关于这本书的信息:(C)2009,Ruby 1.9版

鉴于此错误信息,我不太确定如何识别出哪里出了问题。我很感激任何帮助我理解这里出了什么问题

一个人如何知道识别和解决什么? 我想知道Ruby的CSV功能是否真的这么简单——不需要运行gem/bundle安装

我真的希望能够运行test_code.rb文件,但我无法找出这个错误

谢谢你抽出时间, 帕特里克


注意:所有这些文件都在同一目录中

IRB命令,后跟它生成的错误消息:

2.1.1 :005 > load "test_code.rb"
LoadError: cannot load such file -- csv-reader
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
    from test_code.rb:3:in `<top (required)>'
    from (irb):5:in `load'
    from (irb):5
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/bin/irb:11:in `<main>'
irb第9-11行:

require "irb"

IRB.start(__FILE__)

程序的第一个文件:csv-reader.rb

require 'csv'
require 'book-in-stock'

class CsvReader

  def initialize
    @books_in_stock = []
  end

  def read_in_csv_data(csv_file_name)
    CSV.foreach(csv_file_name, headers: true) do |row|
      @books_in_stock << BookInStock.new(row["ISBN"], row["Amount"])
    end
  end

  def total_value_in_stock
    sum = 0.0
    @books_in_stock.each {|book| sum += book.price}
  end

  def number_of_each_isbn
  end

end

第三个文件:stock-stats.rb

require 'csv-reader'
reader = CsvReader.new
ARGV.each do |csv_file_name|
  STDERR.puts "Processing #{csv_file_name}"
  reader.read_in_csv_data(csv_file_name)
end

puts "Total value = #{reader.total_value_in_stock}"

第四个文件:test_code.rb

# this is the test code file

require 'csv-reader'
require 'book-in-stock'
require 'stock-stats'

# code to call
reader = CsvReader.new
reader.read_in_csv_data("file1.csv")
reader.read_in_csv_data("file2.csv")

puts "Total value in stock = #{reader.total_value_in_stock}"


# code to call
book = BookInStock.new("isbn1", 33.80)
puts "Price = #{book.price}"
puts "Price in cents = #{book.price_in_cents}"
book.price_in_cents = 1234
puts "Price = #{book.price}"
puts "Price in cents = #{book.price_in_cents}"

CSV文件: file1.csv

ISBN, Amount
isbn1, 49.00
isbn2, 24.54
isbn3, 33.23
isbn4, 15.55
文件2.csv

ISBN, Amount
isbn5-file2, 39.98
isbn6-file2, 14.84
isbn7-file2, 43.63
isbn8-file2, 25.55


编辑 在Frederick Cheung建议将require更改为requirerelative(对于csv reader.rb的第1行以外的所有行),脚本正在运行,但一个方法不起作用(见下文) (我确实收到了关于此行的错误: @价格=浮动(价格) 并将其改为@price=price.to_f,运行良好。)

3个问题: ->我将csv文件的标题改为“ISBN,金额”。以前的金额为金额(未资本化)。这是否重要(即页眉大写)

->当我们谈到这个主题时,在下面的#read_in_csv_data方法中,“row”关键字在做什么

->现在,我的代码运行了,“股票总价值”的输出似乎不是csv文件中所有价格的总和。请一位红宝石专家帮我理解为什么会发生这种情况

方法

  def read_in_csv_data(csv_file_name)
    CSV.foreach(csv_file_name, headers: true) do |row|
      @books_in_stock << BookInStock.new(row["ISBN"], row["Amount"])
    end
  end
以下是端子的电流输出:

Total value = []
Price = 33.8
Price in cents = 3380
Price = 12.34
Price in cents = 1234
Total value in stock = [#<BookInStock:0xb8168a60 @isbn="isbn1", @price=0.0>, #<BookInStock:0xb8168740 @isbn="isbn2", @price=0.0>, #<BookInStock:0xb8168358 @isbn="isbn3", @price=0.0>, #<BookInStock:0xb81546f0 @isbn="isbn4", @price=0.0>, #<BookInStock:0xb8156a18 @isbn="isbn5-file2", @price=0.0>, #<BookInStock:0xb8156784 @isbn="isbn6-file2", @price=0.0>, #<BookInStock:0xb81564a0 @isbn="isbn7-file2", @price=0.0>, #<BookInStock:0xb8156248 @isbn="isbn8-file2", @price=0.0>]
Total value=[]
价格=33.8
以美分为单位的价格=3380
价格=12.34
以美分为单位的价格=1234
股票总价值=[#、#、#、#、#、#、#、#、#、#、#]
再次感谢

编辑:非常感谢7Stud对我的每一个问题都给出了非常彻底的后续回答。你帮了大忙。多亏了你的帖子,我学到了一些重要的东西。 编辑: 仍然无法运行代码。 我不确定如何添加/编辑$LOAD_路径,因此我尝试将所有文件放入此目录: 目录:~MY\u RUBY\u HOME/lib/RUBY/site\u RUBY/2.1.0/csv-reader (即/Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site\u ruby/2.1.0/csv阅读器)

但是,我仍然收到相同的错误消息:

 ✘  ~MY_RUBY_HOME/lib/ruby/site_ruby/2.1.0/csv-reader  ruby test_code.rb file1.csv file2.csv
/Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require': cannot load such file -- ./csv_reader (LoadError)
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
    from test_code.rb:1:in `<main>'
✘  ~MY_RUBY_HOME/lib/RUBY/site_RUBY/2.1.0/csv-reader ruby测试代码.rb文件1.csv文件2.csv
/Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site\u ruby/2.1.0/rubygems/core\u ext/kernel\u require.rb:55:“require”中:无法加载此类文件--./csv\u读取器(加载错误)
来自/Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site\u ruby/2.1.0/rubygems/core\u ext/kernel\u require.rb:55:in'require'
来自test_code.rb:1:in`'

require在Ruby的加载路径中搜索文件(存储在全局变量$:或$load\u路径中)

默认情况下,当前目录不在加载路径中(它以前在ruby 1.8和更早版本中),这就是ruby说它找不到csv阅读器的原因

您可以通过操纵$:变量(其行为类似于数组)或使用
-I
选项添加到加载路径

例如,如果您通过执行以下操作启动irb

irb -I.
然后,您的代码应该在没有修改的情况下运行(假设没有其他问题)


最后,您可以切换require语句以使用
require\u relative
-这将定位相对于当前文件的文件
require
在Ruby的加载路径中搜索文件(这存储在全局变量$:或$load\u路径中)

默认情况下,当前目录不在加载路径中(它以前在ruby 1.8和更早版本中),这就是ruby说它找不到csv阅读器的原因

您可以通过操纵$:变量(其行为类似于数组)或使用
-I
选项添加到加载路径

例如,如果您通过执行以下操作启动irb

irb -I.
然后,您的代码应该在没有修改的情况下运行(假设没有其他问题)

最后,您可以将require语句切换为使用
require\u relative
——这将定位相对于当前文件的文件

我从Ruby Pickaxe的书中写了一些代码

是的,但是有很多红宝石鹤嘴锄的书

IRB命令,后跟它生成的错误消息:

2.1.1 :005 > load "test_code.rb"
LoadError: cannot load such file -- csv-reader
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
    from test_code.rb:3:in `<top (required)>'
    from (irb):5:in `load'
    from (irb):5
    from /Users/patrickmeaney/.rvm/rubies/ruby-2.1.1/bin/irb:11:in `<main>'
不要在IRB中运行任何东西。任何事情都不要使用IRB。而是将代码放入文件中,然后运行该文件,例如:

$ ruby my_prog.rb
LoadError:无法加载此文件--csv读取器

如果您需要的文件不在ruby自动搜索的目录中(要查看这些目录,请执行“p$LOAD_PATH”行),则可以在require语句中指定您需要的文件的绝对或相对路径:

require './book_in_stock'
我确实收到了关于这行的错误:@price=Float(price)和 将其更改为@price=price.to_f,运行正常

所以“row”是一个引用“CSV::row”的变量。“CSV::Row”的作用类似于散列,使您能够编写类似Row['ISBN']的内容来检索该列中的值

空格在csv文件中很重要。如果标题行为ISBN,Amount,则列名为“ISBN”和“Amount”(请参见前导空格?)。这意味着没有价值

row['Amount']
row[' Amount']
     ^
     |
i、 它将返回nil,但有一个

row['Amount']
row[' Amount']
     ^
     |
现在,我的代码运行了,似乎“Total value in”的输出 “股票”不是csv文件中所有价格的总和。可以吗 请帮我了解一下
row[' Amount']
     ^
     |
  def total_value_in_stock
    sum = 0.0
    @books_in_stock.each {|book| sum += book.price}
  end
  def total_value_in_stock
    sum = 0.0
    @books_in_stock.each {|book| sum += book.price}
    sum
  end
CSV.foreach(
  csv_file_name, 
  headers: true,
  :converters => :numeric
) do |row| ...
class BookInStock
  attr_reader :isbn
  attr_accessor :price

  def initialize(isbn, price)
    @isbn = isbn
    @price = price  #Float(price)
  end
require 'csv'
require './book_in_stock'

class CsvReader

  def initialize
    @books_in_stock = []
  end

  def read_in_csv_data(csv_file_name)
    CSV.foreach(csv_file_name, headers: true) do |row|
      @books_in_stock << BookInStock.new(row["ISBN"], row["Amount"])
    end
  end

  def total_value_in_stock
    sum = 0.0
    @books_in_stock.each {|book| sum += book.price}
    sum
  end

  def number_of_each_isbn
  end

end
require './csv_reader'

reader = CsvReader.new

ARGV.each do |csv_file_name|
  STDERR.puts "Processing #{csv_file_name}"
  reader.read_in_csv_data(csv_file_name)
end

puts "Total value = #{reader.total_value_in_stock}"
require './csv_reader'
require './book_in_stock'
require './stock_stats'

reader = CsvReader.new
reader.read_in_csv_data("file1.csv")
reader.read_in_csv_data("file2.csv")

puts "Total value in stock = #{reader.total_value_in_stock}"


# code to call
book = BookInStock.new("isbn1", 33.80)
puts "Price = #{book.price}"
puts "Price in cents = #{book.price_in_cents}"
book.price_in_cents = 1234
puts "Price = #{book.price}"
puts "Price in cents = #{book.price_in_cents}"
class BookInStock
  attr_reader :isbn
  attr_accessor :price

  def initialize(isbn, price)
    @isbn = isbn
    @price = Float(price)
  end

  def price_in_cents
    Integer(price*100 + 0.5)
  end

  def price_in_cents=(cents)
    @price = cents / 100.0
  end
end
ISBN,Amount
isbn1,49.00
isbn2,24.54
isbn3,33.23
isbn4,15.55
ISBN,Amount
isbn5-file2,39.98
isbn6-file2,14.84
isbn7-file2,43.63
isbn8-file2,25.55
~/ruby_programs$ ruby test_code.rb file1.csv file2.csv
Processing file1.csv
Processing file2.csv
Total value = 246.32
Total value in stock = 246.32
Price = 33.8
Price in cents = 3380
Price = 12.34
Price in cents = 1234