我正在努力寻找建立1:0,1关系(“可能有一个”或“最多有一个”)关系的最佳方法。我相信这称为Z基数。

例如,假设我有两个类WidgetWidgetTest。并非所有Widget都经过测试,并且测试具有破坏性,因此每个Widget最多可以有一个WidgetTest。还要假设将WidgetTest字段添加到Widget是不合适的。

我希望我的公共(public)界面是:

Widget
    WidgetTest { get; set; }

WidgetTest
    Widget { get; }

模型1:Widget具有WidgetTest属性,并且在数据库中,Widget表具有WidgetTest的唯一受约束的外键。我的DBA争辩说,这将允许在没有Widget的情况下存在WidgetTest记录。
WidgetTable
    WidgetTestId (FK, UQ)

模型2:Widget具有WidgetTest的私有(private)集合,并通过从由公共(public)WidgetTest属性控制的集合中添加或删除单个对象来实现0,1关系。数据库使用WidgetTest将其建模为1:m,它具有Widget唯一受约束的外键。我认为这意味着要采用适合数据库模式的模型(即对我来说需要更多工作)。
WidgetTestTable
    WidgetId (FK, UQ)

哪种型号更好?使用NHibernate哪个更容易实现?还是有第三种方式?

编辑...这就是我最终得到的结果:
public class Widget
{
    // This is mapped in NH using a access strategy
    private IList<WidgetTest> _widgetTests = new List<WidgetTest>(1);

    public WidgetTest
    {
        get { return _widgetTests.FirstOrDefault(); }
        set
        {
            _widgetTests.Clear();
            if (value != null)
            {
                _widgetTests.Add(value);
            }
         }
     }
}

最佳答案

我的方法是在映射中建立一对多关系的模型,但是将“许多”约束为一个项目。这允许可选的一对一,并且还可以确保在保存Widget时持久保存WidgetTest实例。例如:

public class Widget
{
    /// <summary>
    /// This property is ignored by the NHibernate mappings.
    /// </summary>
    public virtual WidgetTest WidgetTest { get; set; }

    /// <summary>
    /// For easier persistence with NHibernate, this property repackages the
    /// WidgetTest property as a list containing a single item. If an
    /// attempt is made to set this property to a list containing more than
    /// one item, an exception will be thrown. But why bother? Just use the
    /// WidgetTest property.
    /// </summary>
    public virtual IList<WidgetTest> WidgetTests
    {
        get
        {
            IList<WidgetTest> widgetTests = new List<WidgetTest>();
            if (this.WidgetTest != null)
            {
                widgetTests.Add(this.WidgetTest);
            }
            return widgetTests;
        }
        set
        {
            if (value != null && value.Count > 1)
            {
                throw new Exception("The WidgetTests collection may not contain more than one item.");
            }
            else if (value != null && value.Count == 1)
            {
                this.WidgetTest = value[0];
            }
            else
            {
                this.WidgetTest = null;
            }
        }
    }
}

关于nhibernate - 建模一对零或一种关系(Z基数),我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/2208796/

10-09 07:26