【问题标题】:Sharing schema with struct children与 struct children 共享 schema
【发布时间】:2017-09-11 06:40:18
【问题描述】:

我正在尝试为数据库文件格式实现解析器。从概念上讲,我正在尝试定义如下结构:

struct Database {
    schema: Vec<FieldDescriptors>,
    records: Vec<Record>,
}

Record 基本上只是一个Vec&lt;u8&gt;。为了从记录中提取一列,它需要引用一个模式(知道要读取哪些字节)。我尝试了几种设计都没有成功:

1) 让Record 结构存储对Database 或架构的引用(偶然发现了这个答案:Why can't I store a value and a reference to that value in the same struct?,我明白它为什么不起作用)。

2) 为记录数据创建不同的类型(存储在数据库结构中),以及可以实际返回适当列的记录(在需要时按需创建)。记录包含对数据的引用和对模式的引用。这工作得很好,除了我希望能够实现 Index 特征来访问记录。不幸的是,index 必须返回一个引用,所以我不能按需返回一个新的代理对象。 (目前也显然不可能做到Implementing Index trait to return a value that is not a reference

我考虑过的其他选项:将架构副本与每条记录一起存储会很浪费,或者将架构存储在一个盒子中并在每条记录中存储对它的引用(似乎最不繁琐,但仍然不令人满意) .

我是否缺少解决此问题的好方法?

【问题讨论】:

  • 使用Rc?仅在解码时传入对模式的引用,而不是作为Record 的属性?单独存储模式,不要捆绑它们?使用 owning_ref?
  • RC 似乎有点矫枉过正,因为架构的生命周期与数据库的生命周期完全相同。我想捆绑它们,因为我认为架构是一个内部细节。 owning_ref 看起来可能是我想要的,但我有点困惑如何使用它。我想我想从这里按照切片示例的 RcRef 进行操作,对吧? kimundi.github.io/owning-ref-rs/owning_ref/index.html

标签: indexing reference rust


【解决方案1】:

您没有发布太多代码,但我想您想使用以下方式从记录中获取列信息:

impl Record {
   fn get_column(&self, index: usize) -> Column {
       // use self.schema to get the column...
   }
}

完全不同的设计是将此代码与架构相关联,并在您需要架构对其执行某些操作时传递&amp;Record。您可以使用外观来保护任何用户不必直接处理模式,外观可以是Database 本身:

struct Schema {
   field_descriptors: Vec<FieldDescriptors>
}

struct Database {
    schema: Schema,
    records: Vec<Record>,
}

impl Schema {
    fn get_column(&self, record: &Record, index: usize) -> Column {
        // use self.field_descriptors to get the column...
    }
}

impl Database {
    fn get_column(&self, row: usize, col_index: usize) -> Column {
        schema.get_column(&self.records[row], col_index)
    }
}

【讨论】:

  • 用户是否还需要对象才能从记录中获取列?我希望他们能做类似database[i].get_column(2) 的事情。理想情况下,用户不必关心架构。
  • @BenJones 如果您通过Database 结构访问它,那么您可以处理那个额外的参数,这样用户就不必这样做了。我更新了代码以包含它。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-05-30
  • 1970-01-01
  • 2019-04-28
  • 2018-08-11
  • 1970-01-01
  • 2014-10-08
相关资源
最近更新 更多