我正在通过学习Ruby Hard the Hard Way练习39,它要求我使用Dump函数列出哈希中的所有内容。我已经搜索并使用了Ruby Documentation on Marshal Dump中的想法,但我相信我写的语法不正确,因为我收到了一个未定义的无方法错误,即使(我认为)我已经定义了它:
ex39f.rb:41:<main>': undefined method
转储&#39; for Dict:Module(NoMethodError)
有没有人能够深入了解组织函数的语法/方法,以便我可以将所有内容转储到哈希中?
容纳哈希和其他方法的模块如下。你会在底部找到我的转储功能:
module Dict
#Creates a new function that makes a Dictionary. This is done through creating the
# aDict variable that has an array in which num_buckets array is placed inside.
# These buckets will be used to hold the contents of the Dict and later aDict.length
# is used to find out how many buckets there are.
def Dict.new(num_buckets=256)
# Initializes a Dict with the given number of buckets.
aDict = []
(0...num_buckets).each do |i|
aDict.push([])
end
return aDict
end
# Converts a string to a number using the bult-in Ruby 'hash' function
# Once I have a number for the key, I use the % operator and aDict.length to get a
# bucket where the remainder can go.
def Dict.hash_key(aDict, key)
# Given a key this will create a number and then convert it to an index for the
# aDict's buckets
return key.hash % aDict.length
end
# Uses hash_key to find a bucket that the key could be in. Using bucket_id I can get
# the bucket where the key could be. By using the modulus operator I know it will fit
# into the aDict array of 256.
def Dict.get_bucket(aDict, key)
# Given a key, find the bucket where it would go.
bucket_id = Dict.hash_key(aDict, key)
return aDict[bucket_id]
end
# Uses get_slot to get the (i, k, v) and returns the v (value) only.
def Dict.get_slot(aDict, key, default=nil)
# Returns the index, key and value of a slot found in a bucket.
bucket = Dict.get_bucket(aDict, key)
bucket.each_with_index do |kv, i|
k, v = kv
if key == k
return i, k, v
end
end
return -1, key, default
end
def Dict.get(aDict, key, default=nil)
# Gets the value in a bucket for the given key or the default.
i, k, v = Dict.get_slot(aDict, key, default=default)
return v
end
def assert(aDict, key)
unless aDict == key
puts "The key cannot be found in the dictionary"
end
end
# Sets a key/value pair by getting the bucket and appending the new (key, value) to it.
# First you have to get the bucket, see if the key already exists, if it does then
# replace it, if it doesn't get replaced then append it.
def Dict.set(aDict, key, value)
# Sets the key to the value, replacing any existing value.
bucket = Dict.get_bucket(aDict, key)
i, k, v = Dict.get_slot(aDict, key)
if i >= 0
bucket[i] = [key, value]
else
bucket.push([key, value])
end
end
# Deletes a key by getting the bucket, searching for key in it and deleting it form the
# array.
def Dict.delete(aDict, key)
# Deletes the given key from the Dict.
bucket = Dict.get_bucket(aDict, key)
(0...bucket.length).each do |i|
k, v = bucket[i]
if key == k
bucket.delete_at(i)
break
end
end
end
# goes through each slot in each bucket and prints out what's in the Dict.
#def Dict.list(aDict)
# Prints out what's in the Dict.
# aDict.each do |bucket|
# if bucket
# bucket.each {|k, v| puts k, v}
# end
# end
#end
def Dict.dump(aDict)
#Prints out each bucket so you can debug it.
Marshal.dump(aDict)
end
end
我试图调用dump函数的脚本如下:
require './dict.rb'
include Dict
# create a mapping of state to abbreviation
states = Dict.new()
Dict.set(states, 'Oregon', 'OR')
Dict.set(states, 'Florida', 'FL')
Dict.set(states, 'California', 'CA')
Dict.set(states, 'New York', 'NY')
Dict.set(states, 'Michigan', 'MI')
# create a basic set of states and some cities in them
cities = Dict.new()
Dict.set(cities, 'CA', 'San Francisco')
Dict.set(cities, 'MI', 'Detroit')
Dict.set(cities, 'FL', 'Jacksonville')
# add some more cities
Dict.set(cities, 'NY', 'New York')
Dict.set(cities, 'OR', 'Portland')
# puts out some cities
puts '-' * 10
puts "NY State has: #{Dict.get(cities, 'NY')}"
puts "OR State has: #{Dict.get(cities, 'OR')}"
# puts some states
puts '-' * 10
puts "Michigan's abbreviation is: #{Dict.get(states, 'Michigan')}"
puts "Florida's abbreviation is: #{Dict.get(states, 'Florida')}"
# do it by using the state then cities dict
puts '-' * 10
puts "Michigan has: #{Dict.get(cities, Dict.get(states, 'Michigan'))}"
puts "Florida has: #{Dict.get(cities, Dict.get(states, 'Florida'))}"
# puts every state abbreviation
puts '-' * 10
#Dict.list(states)
Dict.dump(states)
# puts every city in state
puts '-' * 10
Dict.dump(cities)
#Dict.list(cities)
puts '-' * 10
# by default ruby says "nil" when something isn't in there
state = Dict.get(states, 'Texas')
if !state
puts "Sorry, no Texas."
end
# default values using ||= with the nil result
city = Dict.get(cities, 'TX', 'Does Not Exist')
puts "The city for the state 'TX' is: #{city}"
答案 0 :(得分:0)
我做了一些研究并回到了我第一次尝试通过我在网上找到的另一个资源的确认来解决这个问题。
在模块词典中,我添加了以下内容:
Dict.dump(aDict)
aDict.each do |bucket|
puts bucket
end
end
在我使用的脚本上,我使用了以下调用:
Dict.dump(cities)
Dict.dump(states)
对于那些想知道的人来说,cities / states是我在脚本开头创建的哈希值。存储桶表示存储其散列的键和值的位置。因此,我将散列(即城市和州变量)传递到函数Dict.dump(散列)进行转储,即打印出存储其键和值的所有存储桶。