代码之家  ›  专栏  ›  技术社区  ›  Justin

如何用yaml更新已经实例化的Ruby对象?

  •  2
  • Justin  · 技术社区  · 14 年前

    基本上,我已经有了一个Ruby对象的实例,但是我想从yaml中更新任何实例变量。有一个to ou yaml函数将我的对象转储到yaml。我在找相反的东西。例如,my_obj.from_yaml(yaml_-stufacture),并让它从传入的yaml更新实例变量。

    我是否需要在我的from yaml函数中使用yaml::load并复制每个实例变量?如果是这样的话,有没有一个函数可以用来快速复制那些变量而不需要输入太多的内容?

    Ruby的yaml库是否已经有了一些东西,我可以把对象和yaml传递给它,它就可以做我想做的事情?

    为清晰起见编辑

    这是一个简单的对象,它将存储和加载非常简单的yaml兼容类型,如字符串和整数。

    我最终做了什么

    虽然我回答了这个问题,但我想补充一下我最终做了什么,我的目标猴子补丁

    class Object
    
      def from_yaml(yml)
    
        if (yml.nil?)
          return
        end
    
        yml.instance_variables.each do |iv|
          if (self.instance_variable_defined?(iv))
            self.instance_variable_set(iv, yml.instance_variable_get(iv))
          end
        end
    
      end
    end
    
    3 回复  |  直到 14 年前
        1
  •  1
  •   Mladen Jablanović    14 年前

    你的问题不够清楚。你说的是哪门课?什么样的山药文件?你不能 一切 在yaml和yaml之间序列化。

    假设您的对象只有一组简单的、与yaml兼容类型的实例变量,例如字符串、数字和符号。

    在这种情况下,你通常可以 from_yaml 方法,将yaml文件加载到 key->value 对,遍历它并更新名为 key 具有 value . 这看起来有用吗?如果有用,你需要帮助写这种方法吗?

    编辑:

    您不需要将对象状态保持在散列中—您仍然可以使用ivar和attr_访问器—只需打开一个新模块(例如 YamlUpdateable ,实现一个from-yaml方法,该方法将从从yaml反序列化的散列更新您的ivar,并将模块包含在要从yaml反序列化的任何类中。

        2
  •  1
  •   Sérgio Gomes    14 年前

    据我所知,yaml库本身没有类似的功能;它主要用于转储和读取数据,而不是使其在内存和磁盘上保持最新。如果您计划将数据保存在内存和磁盘上,以最少的麻烦实现同步,您是否考虑过类似的数据持久性库? ActiveRecord Stone ?

    如果您仍然热衷于使用yaml库,并且假设您没有许多不同的类来持久化,那么简单地编写一个小的“updater”方法来更新给定类似对象的类的对象可能是有意义的。或者,您可以重新编写应用程序,以确保您可以简单地从yaml重新加载所有对象,而不必更新它们(即,转储旧对象并创建新对象)。

    另一种选择是使用元编程来读取对象的属性并相应地更新它们,但这似乎很容易出错并且很危险。

        3
  •  -1
  •   sintaxi    14 年前

    你要找的是 merge 命令。

    // fetch yaml file
    yml = YAML.load_file("path/to/file.yml")
    
    // merge variables
    my_obj.merge(yml)