从磁盘上的文件中读取哈希值
下面是一个哈希值,我将其保存到文件中供以后阅读。从磁盘上的文件中读取哈希值
my_hash = {-1 => 20, -2 => 30, -3 => 40}
File.open("my_file.txt", "w") { |f| f.write my_hash }
#how it looks opening the text file
{-1 => 20, -2 => 30, -3 => 40}
当我去读它时,是我的问题所在。 (下面的代码是从顶部分开)
my_hash = File.foreach("my_file.txt") { |f| print f }
p my_hash
#=> {-1 => 20, -2 => 30, -3 => 40}nil
是nil
弄乱我的code..not知道如何其余摆脱如果。只是为了清晰起见,其余代码...
back_up_hash = {-1 => 20}
if my_hash.nil?
my_hash = back_up_hash
end
那个小nil
总是让my_hash等于back_up_hash。我需要.nil?
以防万一文件没有散列,否则问题会进一步下移。
我也试着阅读(啜食?..它是一个小文件)这样的文件....
my_hash = File.read("my_file.txt") { |f| print f }
p my_hash
=> "{-1 => 20, -2 => 30, -3 => 40}"
# not sure how to get it out of string form...and I have searched for it.
将简单数据结构保存到文件的正确方法是对它们进行序列化。在这种特殊情况下,使用JSON可能是一个不错的选择:
# save hash to file:
f.write MultiJson.dump(my_hash)
# load it back:
p MultiJson.load(file_contents)
请记住,JSON是只能够序列简单,内置的数据类型(字符串,数字,数组,哈希和类似)。您将无法以这种方式序列化和反序列化自定义对象,而无需额外的工作。
如果您还没有MultiJson
,请使用JSON
来代替它。
我更感谢这个答案更多的几天后。我完全使用Json。 – melee
如果你想利用在磁盘上是{-1 => 20, -2 => 30, -3 => 40}
并从中散,你想其内容的文件:
hash_str = File.read('my_file.txt')
my_hash = eval(hash_str) # Treat a string like Ruby code and evaluate it
# or, as a one-liner
my_hash = eval(File.read('my_file.txt'))
你在做什么在文件中读取并打印到屏幕上,一次一行。 'print'命令不会转换数据,并且foreach
方法不会将其生成的数据映射到您的数据块中。这就是为什么你得到nil
为您的my_hash
。如果你有一个Ruby对象(比如一个Hash),你需要将它保存到磁盘并稍后加载,你可能需要使用Marshal
模块(内置于Ruby):
$ irb
irb(main):001:0> h = {-1 => 20, -2 => 30, -3 => 40}
#=> {-1=>20, -2=>30, -3=>40}
irb(main):002:0> File.open('test.marshal','wb'){ |f| Marshal.dump(h, f) }
#=> #<File:test.marshal (closed)>
$ irb # later, a new irb session with no knowledge of h
irb(main):001:0> h = File.open('test.marshal'){ |f| Marshal.load(f) }
#=> {-1=>20, -2=>30, -3=>40}
我已经成功与这些2点简单的方法:
def create_json_copy
File.open("db/json_records/stuff.json","w") do |f|
f.write("#{@existing_data.to_json}")
end
end
def read_json_copy
@json = JSON.parse(File.read("db/json_records/stuff.json")).as_json.with_indifferent_access
@json.each do |identifier,record|
existing_record = Something.find_by(some_column: identifier)
if !existing_record
Something.create!(record.except(:id).except(:created_at).except(:updated_at))
end
end
end
注:@existing_data
是组织为{ some_identifier: record_objet, ... }
一个Ruby的Hash。在将它写入文件之前,我将它称为.to_json,然后在读取我之后之后是.as_json
,with_indifferent_access
在这里并不是真的需要,因此只要您替换excepts
内的符号,就可以关闭它。
我不熟悉Ruby,但我很肯定你必须将对象序列化到一个文件,而不是只写数据结构表示。如果我不得不猜测,我会说这是你的问题的一部分。 –
您可能有兴趣使用['Marshal'模块](https://ruby-doc.org/core-2.2.2/Marshal.html)将本地Ruby对象转储到磁盘并在以后快速加载它们。 – Phrogz
@用户。是的,该线程对我来说确实有一个可行的答案......我之前就看到了它。不幸的是,我有点不知所措,如果答案对我的情况来说不太理想,它会让我失望。感谢您指出该链接。元帅看起来是一个很好的解决方案。 – melee