自己开发轻量级ORM(三)
上一篇中简单分享了下ORM的设计思路。现在开始讲如何用代码来实现上篇的设计模型。
我们建2个类库来分别抽象数据库表结构关系映射和SQL增删改查操作。
打开VS2010,新建2个类库。分别起名为Model,和DAL。

Model层为数据库表结构关系映射
DAL层为 SQL增删改查操作的方法抽象封装
我们先从Model层开始。
数据库的表会包含表名,字段名称,字段类型,主键,外键等主要元素。我们在项目中为每张表建立一个Model类来抽象描述。
在Model类中我们定义常量TableName,用来描述数据库表名称。为表的字段逐一添加Model类属性,属性名和字段名相同。
由于SQL字段类型和.net数据类型不一致,我们在字段属性上添加自定义特性类DBType来描述对应的SQL字段类型。
字段会有主键,外键标识或者是虚拟字段标识。我们在字段属性上添加自定义特性类DBField来描述他们。
如:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Model.Entities;
using System.Data;
namespace Model
{
[Serializable]
public class EmpInfoModel : BaseEntity
{
/// <summary>是否可以修改
/// </summary>
public const bool isCanMod = false;
/// <summary>数据库表名
/// </summary>
public const String TableName = "EmpInfo";
public EmpInfoModel()
{ } private string _Id;
private string _Name;
private int? _isAllMoneyCheck;
private Guid? _MyGuid;
private Int16? _MySmallint;
private bool? _MyBool;
private string _Myntext;
[DBField(KeyType = DbKeyType.PK)]//主键标识
[DBType(SqlDBType = SqlDbType.NVarChar)]//字段对应SQLSERVER数据库字段类型
public virtual string Id
{
set { _Id = value; }
get { return _Id; }
} public string Name
{
set { _Name = value; }
get { return _Name; }
} public int? isAllMoneyCheck
{
set { _isAllMoneyCheck = value; }
get { return _isAllMoneyCheck; }
} [DBType(SqlDBType = SqlDbType.UniqueIdentifier)]//字段对应SQLSERVER数据库字段类型
public Guid? MyGuid
{
set { _MyGuid = value; }
get { return _MyGuid; }
} [DBType(SqlDBType = SqlDbType.SmallInt)]//字段对应SQLSERVER数据库字段类型
public Int16? MySmallint
{
set { _MySmallint = value; }
get { return _MySmallint; }
} [DBType(SqlDBType = SqlDbType.Bit)]//字段对应SQLSERVER数据库字段类型
public bool? MyBool
{
set { _MyBool = value; }
get { return _MyBool; }
}
[DBType(SqlDBType = SqlDbType.NText)]//字段对应SQLSERVER数据库字段类型
public string Myntext
{
set { _Myntext = value; }
get { return _Myntext; }
}
}
}
我在Model类库下添加DbKeyType类,TableJoinType类,DBFieldAttribute类,DBJoinAttribute类,DBTableAttribute类,DBTypeAttribute类。

DbKeyType类为字段键值枚举类,枚举值包含字段否为主键,外键,无,和虚拟字段。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace Model.Entities
{
/// <summary>
/// 创建人:雷旭鹏(leo) 2014-1-13
/// 联系方式:leixupeng823@163.com
/// </summary>
public enum DbKeyType:int
{
Filed = ,
PK = ,
FK = ,
/// <summary>只用于承载数据
/// </summary>
DataFiled =
}
}
TableJoinType为表连接类型枚举类
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace Model.Entities
{
/// <summary>
/// 创建人:雷旭鹏(leo) 2014-1-13
/// 联系方式:leixupeng823@163.com
/// </summary>
public enum TableJoinType : int
{
INNER_JOIN = ,
LEFT_JOIN = ,
RIGHT_JOIN =
}
}
DBFieldAttribute类为字段键值特性标识类
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace Model.Entities
{
/// <summary>字段特性
/// 创建人:雷旭鹏(leo) 2014-1-13
/// 联系方式:leixupeng823@163.com
/// </summary>
[AttributeUsage(AttributeTargets.Property, Inherited = false)]
public sealed class DBFieldAttribute : Attribute
{
/// <summary>字段名称
/// </summary>
public string FieldName
{
get;
set;
}
/// <summary>键类型
/// </summary>
public DbKeyType KeyType
{
get;
set;
}
/// <summary>字段数据类型
/// </summary>
public Type PropertyType
{
get;
set;
}
/// <summary>构造函数
/// </summary>
public DBFieldAttribute()
{ }
}
}
DBJoinAttribute类为关系表连接类型特性标识类
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace Model.Entities
{
/// <summary>链接属性
/// 创建人:雷旭鹏(leo) 2014-1-13
/// 联系方式:leixupeng823@163.com
/// </summary>
[AttributeUsage(AttributeTargets.Property, Inherited = false)]
public sealed class DBJoinAttribute : Attribute
{
/// <summary>主键
/// </summary>
public string PK
{
get;
set;
}
/// <summary>外键
/// </summary>
public string FK
{
get;
set;
}
/// <summary>表连接关系
/// </summary>
public TableJoinType JoinType
{
get;
set;
}
/// <summary>构造函数
/// </summary>
public DBJoinAttribute()
{ }
}
}
DBTableAttribute类用于连接是标识相应表名
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace Model.Entities
{
/// <summary>所属表属性
/// 创建人:雷旭鹏(leo) 2014-1-13
/// 联系方式:leixupeng823@163.com
/// </summary>
[AttributeUsage(AttributeTargets.Property, Inherited = false)]
public sealed class DBTableAttribute : Attribute
{
/// <summary>表名称
/// </summary>
public string TableName
{
get;
set;
}
/// <summary>表昵称
/// </summary>
public string TableNickName
{
get;
set;
}
/// <summary>构造函数
/// </summary>
public DBTableAttribute()
{
}
}
}
DBTypeAttribute类为标识字段对应SQLSERVER字段类型标识类
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;
namespace Model.Entities
{
[AttributeUsage(AttributeTargets.Property, Inherited = false)]
public sealed class DBTypeAttribute : Attribute
{
/// <summary>SQL数据库字段类型
/// </summary>
public SqlDbType SqlDBType
{
get;
set;
}
/// <summary>构造函数
/// </summary>
public DBTypeAttribute()
{
}
}
}
通过添加上面的类,我们现在可以对数据库表进行抽象,用对应的特性标识字段是否为主键,外键或者为虚拟字段,SQL字段于.net类型的转换关系。各Model类之间的连接关系。
自己开发轻量级ORM(三)的更多相关文章
- 自己开发轻量级ORM(一)
在开发ORM之前,先简单的介绍下ORM的基本概念. 对象关系映射(Object Relational Mapping,简称ORM)是一种为了解决面向对象与关系数据库存在的互不匹配的现象的技术. 简单的 ...
- 自己开发轻量级ORM(二)
上一篇简单的对轻量级ORM开发开了个头.这篇主要聊下ORM框架的设计思路. ORM本质上是对数据库操作的抽象.大体上我将其分为对数据结构的抽象和对执行方法的抽象. 我的ORM设计图: ORM框架需要完 ...
- 【从零开始搭建自己的.NET Core Api框架】(三)集成轻量级ORM——SqlSugar:3.1 搭建环境
系列目录 一. 创建项目并集成swagger 1.1 创建 1.2 完善 二. 搭建项目整体架构 三. 集成轻量级ORM框架——SqlSugar 3.1 搭建环境 3.2 实战篇:利用SqlSuga ...
- 轻量级ORM框架 QX_Frame.Bantina(一、框架简介)
轻量级ORM框架QX_Frame.Bantina系列讲解(开源) 一.框架简介 http://www.cnblogs.com/qixiaoyizhan/p/7417467.html 二.框架使用方式介 ...
- [翻译]现代java开发指南 第三部分
现代java开发指南 第三部分 第三部分:Web开发 第一部分,第二部分,第三部分 =========================== 欢迎来到现代 Java 开发指南第三部分.在第一部分中,我们 ...
- .NET轻量级ORM框架Dapper入门精通
一.课程介绍 本次分享课程包含两个部分<.NET轻量级ORM框架Dapper修炼手册>和<.NET轻量级ORM框架Dapper葵花宝典>,阿笨将带领大家一起领略轻量级ORM框架 ...
- .NET轻量级ORM组件Dapper葵花宝典
一.摘要 为什么取名叫<葵花宝典>? 从行走江湖的世界角度来讲您可以理解为一本"武功秘籍",站在我们IT编程的世界角度应该叫"开发宝典". 如果您在 ...
- 连表查询都用Left Join吧 以Windows服务方式运行.NET Core程序 HTTP和HTTPS的区别 ASP.NET SignalR介绍 asp.net—WebApi跨域 asp.net—自定义轻量级ORM C#之23中设计模式
连表查询都用Left Join吧 最近看同事的代码,SQL连表查询的时候很多时候用的是Inner Join,而我觉得对我们的业务而言,99.9%都应该使用Left Join(还有0.1%我不知道在 ...
- Farseer.net轻量级ORM开源框架 V1.x 入门篇:表的数据操作
导航 目 录:Farseer.net轻量级ORM开源框架 目录 上一篇:Farseer.net轻量级ORM开源框架 V1.x 入门篇:表实体类映射 下一篇:Farseer.net轻量级ORM开源框 ...
随机推荐
- 13款Linux运维比较实用的工具
本文介绍几款Linux运维比较实用的工具,希望对Linux管理员有所帮助. 1.查看进程占用带宽情况-Nethogs Nethogs 是一个终端下的网络流量监控工具可以直观的显示每个进程占用的带宽. ...
- 苹果App Store开发者帐户从申请,验证,到发布应用(2)
app store付费 上面已经介绍了app store id的注册了,下面在注册基础上,介绍一下app store的付费. 在上面注册成功之后,会收到一封邮件. 1.收到邮件Thank Yo ...
- X-006 FriendlyARM tiny4412 u-boot移植之Debug串口用起来
<<<<<<<<<<<<<<<<<<<<<<<<< ...
- C# 计算文件的HASH
/// <summary> /// 提供用于计算指定文件哈希值的方法 /// <example>例如计算文件的MD5值: /// <code> /// String ...
- 原生JavaScript之“淘宝轮播图”
轮播图是我们学习原生js的必经之路 它包含很多基本知识的运用,像this的使用,DOM的操作,还有setInterval的使用和清除,浮动与定位等等,很好的考察了我们的基础知识牢不牢固, 话不多说,直 ...
- 谈谈NIO和IO
Channel,Buffer 和 Selector 构成了核心的API. 其它组件,如Pipe和FileLock,只不过是与三个核心组件共同使用的工具类. Channel和Buffer 基本上,所有的 ...
- 轻轻的扩展了一下IEnumerable<T>
今天用EF写东西玩,觉得IEnumerable里面除了where().select(),是不是能添加点其他方法呢. 想做就做,F12到方法定义: public static IEnumerable&l ...
- [转python 父类可以调用子类的方法
问题描述:我也是在读500 Line 里满的DBDB 的代码时发现的,python的父类可以调用子类的方法,这跟平常习惯的理解方式很不一样,所以就查了下原因,记录如下: 1.现象:最近使用到了So ...
- 【MongoDb基础】插入数据
以mydb为事例数据库. 切换到mydb数据库. use mydb 1. insert函数. db.users.insert({name:"Derek",age:18}) 该函数会 ...
- cf747 D. Winter Is Coming
天呢,这个题2333333,真是被各种卡.完蛋完蛋完蛋.IQ------------: #include<bits/stdc++.h> #define lowbit(x) x&(- ...