首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Nhibernate非空属性引用空值或瞬态值Tec.Core.Model.Budget.oInvestmentCode。

Nhibernate非空属性引用空值或瞬态值Tec.Core.Model.Budget.oInvestmentCode。
EN

Stack Overflow用户
提问于 2014-02-25 02:36:59
回答 2查看 3K关注 0票数 2

早上好,

我对NHibernate非常陌生。我想在我的新项目中使用它,但是我遇到了一个外键引用的问题。我不知道为什么会发生这个问题。

显示的错误消息是:not-null property references a null or transient value Tec.Core.Model.Budget.oInvestmentType

下面是我的表模式:

这是我的映射文件

机场

Airport.hbm.xml

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8" ?> 
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2">   
<class name="Tec.Core.Model.Airport, Tec.Core" table="tblAirport" lazy="false">
    <id name="ID" column="AirportID" unsaved-value="0">
      <generator class="identity" />
    </id>
    <property name="AirportCode" column="AirportCode" />
    <property name="AirportFullName" column="AirportFullName" />

    <bag name="Budgets" table="tblBudget" inverse="true" cascade="save-update">
      <key column="AirportID" />
      <one-to-many class="Tec.Core.Model.Budget, Tec.Core" />
    </bag>
</class> 
</hibernate-mapping>

Airports.cs

代码语言:javascript
复制
public class Airport:Entity<int> 
{
    private string _airportCode="";
    private string _airportFullName="";
    private IList<Budget> _airportBudgets = new List<Budget>();

    private Airport() { }
    public Airport(string AirportCode, string AirportFullName) {
        this._airportCode = AirportCode;
        this._airportFullName = AirportFullName; 
    }                
     public  string AirportCode  {
        get { return _airportCode; }
        set { _airportCode = value; }
    }
    public  string AirportFullName {
        get { return _airportFullName; }
        set { _airportFullName = value; }
    }
    public IList<Budget> Budgets {
        get { return new List<Budget>(_airportBudgets).AsReadOnly(); }
        protected set { _airportBudgets = value; }
    }
    public void AddBudget(Budget air_budget){
        if (air_budget != null && !_airportBudgets.Contains(air_budget)){
            air_budget.oAirport = this; 
            _airportBudgets.Add(air_budget);
        }
    }

    public override int GetHashCode(){
        return (GetType().FullName + "|" + _airportCode.GetHashCode()).GetHashCode();
    }

}

InvestmentCode

InvestmentCode.hbm.xml

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8" ?> 
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2">   
<class name="Tec.Core.Model.InvestmentCode, Tec.Core" table="tblInvestmentCode" lazy="false">
    <id name="ID" column="InvestmentCodeID" unsaved-value="0">
      <generator class="identity" />
    </id>
    <property name="InvCode" column="InvestmentCode" />
    <property name="InvCodeNote" column="InvestmentCodeNote" />

    <bag name="Budgets" table="tblBudget" inverse="true" cascade="save-update">
      <key column="InvestmentCodeID" />
      <one-to-many class="Tec.Core.Model.Budget, Tec.Core" />
    </bag>
  </class> 
</hibernate-mapping>

InvestmentCode.cs

公共类InvestmentCode:实体{ 私有字符串_investmentCode=“;私有字符串_investmentCodeNote=”;私有IList _lstinvestmentCodeBudgets =新列表();私有InvestmentCode() {} public InvestmentCode(string investmentCode,string InvestmentCodeNote) { this._investmentCode = investmentCode;}公共字符串InvCodeNote { get {返回_investmentCodeNote;} set { _investmentCodeNote = value;}}公共IList预算{ get {返回新列表( _lstinvestmentCodeBudgets ).AsReadOnly();}受保护的集合{_lstinvestmentCodeBudgets=值;}公开无效!_lstinvestmentCodeBudgets.Contains(investment_code_budget)){ AddBudget(预算investment_code_budget) { if (investment_code_budget != null &investment_code_budget investment_code_budget.oInvestmentCode = this;_lstinvestmentCodeBudgets.Add(investment_code_budget);)}}公共覆盖int GetHashCode(){ GetType().FullName+“AC.26”+_investmentCode.GetHashCode().GetHashCode();}

InvestmentType

InvestmentType.hbm.xml

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8" ?> 
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2">   
<class name="Tec.Core.Model.InvestmentType, Tec.Core" table="tblInvestmentType" lazy="false">
    <id name="ID" column="InvestmentTypeID" unsaved-value="0">
      <generator class="identity" />
    </id>
    <property name="InvestmentTypeNote" column="InvestmentTypeNote" />    

    <bag name="Budgets" table="tblBudget" inverse="true"  cascade="save-update">
      <key column="InvestmentTypeID" />
      <one-to-many class="Tec.Core.Model.Budget, Tec.Core" />
    </bag>
</class> 
</hibernate-mapping>

InvestmentType.cs

公共类InvestmentType:实体{ 私有字符串_investmentTypeNote=“;私有IList _lstInvestmentTypeBudgets =新列表();私有InvestmentType() {} public InvestmentType(string InvestmentTypeNote){ this._investmentTypeNote = InvestmentTypeNote;}公共字符串InvestmentTypeNote { get {返回_investmentTypeNote;} set { _investmentTypeNote = value;} public IList预算{ get {返回新列表(_lstInvestmentTypeBudgets).AsReadOnly();}受保护的集合{ _lstInvestmentTypeBudgets =值;}公共无效AddBudget(预算investment_type_budget) { if (investment_type_budget != null && _lstInvestmentTypeBudgets investment_type_budget.oInvestmentType = this;_lstInvestmentTypeBudgets.Add(investment_type_budget);)}}公共覆盖int GetHashCode(){ GetHashCode (GetType().FullName +“AC.26”+GetType})}

预算

Budget.hbm.xml

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8" ?> 
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2">   
<class name="Tec.Core.Model.Budget, Tec.Core" table="tblBudget" lazy="false">
    <id name="ID" column="BudgetID" unsaved-value="0">
      <generator class="identity" />
    </id>
    <property name="BudgetAmount" column="BudgetAmount" />
    <property name="BudgetYear" column="BudgetYear" />

    <many-to-one name="oAirport" column="AirportID"
      class="Tec.Core.Model.Airport, Tec.Core" not-null="true" />
    <many-to-one name="oInvestmentCode" column="InvestmentCodeID"
      class="Tec.Core.Model.InvestmentCode, Tec.Core" not-null="true" />
    <many-to-one name="oInvestmentType" column="InvestmentTypeID"
      class="Tec.Core.Model.InvestmentType, Tec.Core" not-null="true" />  
</class> 
</hibernate-mapping>

Budget.cs

public class Budget:Entity<long> { private float \_budgetAmount; private int \_budgetYear; private InvestmentType \_investmentType; private InvestmentCode \_investmentCode; private Airport \_airport; public Budget() { } public float BudgetAmount { get{return \_budgetAmount; } set{\_budgetAmount = value;} } public int BudgetYear { get{return \_budgetYear; } set{\_budgetYear = value;} } public Airport oAirport{ get{return \_airport; } set{\_airport = value;} } public InvestmentType oInvestmentType{ get{return \_investmentType; } set{\_investmentType = value;} } public InvestmentCode oInvestmentCode { get{return \_investmentCode ; } set{\_investmentCode = value;} } public override int GetHashCode(){ return (GetType().FullName + "|" + \_airport.GetHashCode() +"|"+ \_investmentCode.GetHashCode()+"|"+ \_investmentType.GetHashCode()).GetHashCode(); } }

在我的Default.asp.cs里

我有以下代码:

代码语言:javascript
复制
        Airport objA = new Airport("NA", "New Airport")
        InvestmentCode objIC = new InvestmentCode("1000", "ABCD");
        InvestmentType objIT = new InvestmentType("Capex");

        Budget objBg = new Budget();
        objBg.oAirport = objA;
        objBg.oInvestmentCode = objIC;
        objBg.oInvestmentType = objIT;
        objBg.BudgetAmount = 10000;
        objBg.BudgetYear = 2014;

        objA.AddBudget(objBg);
        AirportDao.SaveOrUpdate(objA);

        objIC.AddBudget(objBg);
        daoFactory.GetInvestmentCodeDao().Save(objIC);  //Error occur here not-null property references a null or transient value Tec.Core.Model.Budget.oInvestmentType


        objIT.AddBudget(objBg);            
        daoFactory.GetInvestmentTypeDao().Save(objIT);     
EN

回答 2

Stack Overflow用户

发布于 2014-02-25 02:44:40

我不会把我的生命押在上面..。但我要说你的问题是:

代码语言:javascript
复制
public IList<Budget> Budgets {
    get { return new List<Budget>(_lstinvestmentCodeBudgets).AsReadOnly(); }
    protected set { _lstinvestmentCodeBudgets = value; }
}

此代码按以下顺序调用:

代码语言:javascript
复制
objA.AddBudget(objBg);
AirportDao.SaveOrUpdate(objA);

objA被持久化。objBg也是级联和持久化的。这意味着NHiberante会跟踪对NHiberante的引用。

那你就把这叫做:

代码语言:javascript
复制
objIC.AddBudget(objBg);

按预期将预算添加到列表中。我们把这份名单叫做“名单A”。

然后你去打电话给保存:

代码语言:javascript
复制
daoFactory.GetInvestmentCodeDao().Save(objIC);

当NHibernate开始从您的实体读取值时。这是你的灵感来源:

代码语言:javascript
复制
get { return new List<Budget>(_lstInvestmentTypeBudgets).AsReadOnly(); }

你已经把你的财产包装在一个新的列表中了。所以现在,这是“名单B”。不是NHibernate所期望的“列表A”。“名单B”没有被坚持。所以NHibernate说:“等等.你想坚持我在更新中没有跟踪的东西”。

尝试将您的getter更改为:

代码语言:javascript
复制
get { return _lstInvestmentTypeBudgets; }

..and看看这是否有效。应该..。因为你要返回相同的实例。

票数 0
EN

Stack Overflow用户

发布于 2014-02-25 03:03:09

地图需要稍加修正。预算是一个与机场、投资和InvestmentCode有关的实体。预算不能像子类一样添加到这里的其他类中,因为这里没有任何人与许多类的关系。因此,请从这三个类中删除addBudget方法,并将以下方法添加到Budget类-> AddAirport, AddInvestmentCode, AddInvestmentType中。Update:通过从机场、投资类型和代码中移除指向预算类的袋子,从而相应地更正映射

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/22003511

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档