博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
NHibernate之旅(8):巧用组件之依赖对象
阅读量:6969 次
发布时间:2019-06-27

本文共 3849 字,大约阅读时间需要 12 分钟。

本节内容

  • 引入
  • 方案1:直接加入
  • 方案2:巧用组件
  • 实例分析
  • 结语

引入

通过前面7篇的学习,有点乏味了~~~这篇来学习一个技巧。大家一起想想假设我要在Customer类中实现一个Fullname属性(就是Firstname和Lastname的组合)该怎么做呢?

方案1:直接加入

“我知道!改动Customer类,加入一个Fullname属性!即Customer.Fullname!”

“恩,全然正确......”

“这就意味着在Customer类中把Firstname和Lastname两个属性又一次改动组合为Fullname属性。这种话。假设有其他的类(像Vendor、Shiper)使用了Firstname和Lastname两个属性,这就须要改动非常多业务逻辑。那你的麻烦可就大了,还有什么方法吗?”

“.........”

方案2:巧用组件

NHibernate中。提供了组件(Component)和动态组件来帮助我们完毕这件事情。事实上组件在NHibernate中为了不同目的被反复使用。这里我们使用它来依赖对象

映射文件里,<component>元素把子对象的一些属性映射为父类相应的表的一些字段。然后,组件能够定义它们自己的属性、组件或者集合。

以下用两幅图显示组件和动态组件两个节点映射属性:

看看这些映射属性:

  • access(默认property):NHibernate用来訪问属性的策略
  • class(默认通过反射得到的属性类型):组件(子)类的名字
  • insert:被映射的字段是否出如今SQL的INSERT语句中
  • name:属性名propertyName
  • update:被映射的字段是否出如今SQL的UPDATE语句中
  • <property>子元素:为组件(子)类的一些属性与表字段之间建立映射
  • <parent>子元素:在组件类内部就能够有一个指向其容器的实体的反向引用

<dynamic-component>元素同意一个IDictionary作为组件映射,当中属性名相应字典中的键。这又是使用组件的还有一种使用方法。

知道上面的知识,我们该想想上面的问题该怎样利用组件来实现了吧。

实例分析

我们用一幅图来展示我们这节所说的一切:

開始动手吧。

1.新建Name类

namespace DomainModel.Entities{    public class Name    {        public string Firstname { get; set; }        public string Lastname { get; set; }        public string Fullname        {            get            {                return Firstname + " " + Lastname;            }        }    }}

简单的说。这个类用于组合Fullname属性。

2.改动Customer类

namespace DomainModel.Entities{    public class Customer    {        public virtual int CustomerId { get; set; }        public virtual int Version { get; set; }        public virtual Name Name { get; set; }    }}

改动Customer类。去除原来的Firstname和Lastname属性,加入Name属性。

这时Name作为Customer的一个组成部分。须要注意的是:和原来Firstname和Lastname属性一样。须要对Name的持久化属性定义getter和setter方法,但不须要实现不论什么的接口或声明标识符字段。

3.改动Customer映射

xml
version
="
1.0"
encoding
="
utf-8"
?

> <

hibernate-mapping
xmlns
="
urn:nhibernate-mapping-2.2"
assembly
="
DomainModel"
namespace
="
DomainModel"
> <
class
name
="
DomainModel.Entities.Customer,DomainModel"
table
="
Customer"
> <
id
name
="
CustomerId"
column
="
CustomerId"
type
="
Int32"
unsaved-value
="
0"
> <
generator
class
="
native"
></
generator
> </
id
> <
version
name
="
Version"
column
="
Version"
type
="
integer"
unsaved-value
="
0"
/> <
component name="Name" class="DomainModel.Entities.Name,DomainModel"> <property name="Firstname" column ="Firstname" type="string" length="50" not-null="false" unique-key="UC_CustomerName"/> <property name ="Lastname" column="Lastname" type="string" length="50" not-null="false" unique-key="UC_CustomerName"/> </component
> </
class
> </
hibernate-mapping
>

首先定义Component的一些属性,指定属性名和组件映射的类名。再使用<property>子元素,为Name类的Firstname、Lastname属性与表字段之间建立映射。

是不是非常easy~~

这时Customer表中还是CustomerId、Version、Firstname、Lastname字段。全然不须要改动数据库表结构哦。

这里须要注意两点:

  1. 就像全部的值类型一样,组件不支持共享引用。

    组件的值为空从语义学上来讲是专有的。

    每当又一次载入一个包括组件的对象,假设组件的全部字段为空。那么NHibernate将假定整个组件为空。对于绝大多数目的。这样假定是没有问题的。

  2. 组件的属性能够是NHibernate类型(包括集合、多对一关联以及其他组件)。嵌套组件不应该作为特殊的应用被考虑。NHibernate趋向于支持设计细粒度的对象模型。

4.编写方法

这时,我们须要改动或者又一次编写新的方法来实现我们想要的逻辑。

public IList
ReturnFullName(string firstname, string lastname){ return _session .CreateQuery("select from Customer c where c.Name.Firstname=:fn and c.Name.Lastname=:ln") .SetString("fn", firstname) .SetString("ln", lastname) .List
();}

如今。我们訪问Customer的Firstname、Lastname属性,仅仅须要在原来的基础上通过Name訪问。比如上面改动的情况,看看上面图片上怎么訪问的吧。一目了然。

假设我们要加入一个Customer怎么办呢?代码片段例如以下所看到的:

var customer = new Customer() { Name = new Name() { Firstname = "YJing", Lastname = "Lee" } };

5.測试方法

有了上面的方法,我们编写一个測试用例測试一下这种方法吧:看看结果測试成功,OK。

[Test]public void ReturnFullNameTest(){    IList
customers = _relation.ReturnFullName("YJing","Lee"); foreach (Customer c in customers) { Assert.AreEqual("YJing Lee", c.Name.Fullname); }}

结语

这一篇像大家介绍一个使用组件技巧。通过组件能够改善我们的对象模型,而数据库结构不须要变化。通过这一篇的技巧,利用组件来映射来依赖对象,能够很连贯的引入NHibernate中的多表映射关系、集合等内容,这些才是NHibernate中的亮点。就连LINQ都比只是它。从下篇開始就来学习NHibernate中的闪光点。

转载地址:http://xtisl.baihongyu.com/

你可能感兴趣的文章
Nginx if 条件判断
查看>>
联想y460 +centos6.4 64位 开启无线热点Ap
查看>>
Htc t528w root教程
查看>>
Python 标准库中的装饰器
查看>>
Linux下查看和添加环境变量
查看>>
spark2.x由浅入深深到底系列六之RDD java api详解四
查看>>
jmeter+ant+jenkins
查看>>
Linux基础命令---grep
查看>>
Linux基础命令---cancel取消打印任务
查看>>
理解ORACLE数据库字符集
查看>>
Top Coder算法题目浏览器
查看>>
为SharePoint 2016 配置SQL 2016的always on 模式(二)
查看>>
PHP 选择排序法
查看>>
使用css3做立体效果!
查看>>
CIO的管理经
查看>>
ssh故障解决一例
查看>>
linux学习笔记-第十一课-shell基础
查看>>
当Ctrl+Alt+Del失效时,你需要用net user 来改密码
查看>>
C++的变量作用域
查看>>
ES搭建
查看>>