DataContext的讨论(1)

[索引页]

DataContext的讨论(1):

谢谢访问我的blogs!
本来计划DataContext是一篇写完的,但太长拉,不是很好.所以就分成两部分,第二部分会有disconnect work,写LINQ to SQL与传统的ORM不同和更多吧.



一.是使用ObjectDumper


ObjectDumper: A utility for writing the output from a LINQ query to the screen in text mode.

这个对象就是通过反射你传入的对象的元素和域,再将他们反射出来的值输出到Console Windons,

None.gif ObjectDumper.Write(custs);



二:对LINQ 使用collections的总结


List<T>

System.Collections.Generic.List<T>
■ System.Collections.Generic.LinkedList<T>
■ System.Collections.Generic.Queue<T>
■ System.Collections.Generic.Stack<T>
■ System.Collections.Generic.HashSet<T>
■ System.Collections.ObjectModel.Collection<T>
■ System.ComponentModel.BindingList<T>

Generic dictionaries

System.Collections.Generic.Dictionary<TKey,TValue>
■ System.Collections.Generic.SortedDictionary<TKey, TValue>
■ System.Collections.Generic.SortedList<TKey, TValue>

主要也就是上面这两个.一般LINQ 查询的数据其实就是查询list.



三:相比一下LINQ,Query,LINQ to SQL有什么不同


QueryLINQ LINQ to SQL
Item 
Query variable
return type
Data sourceIEnumerable IQueryablespecification From/from
equivalentFiltering Where/where
equivalentGrouping
Groupby
equivalentSelectingSelect/select
equivalentJoins joinAssociation attribute
他们使用的组件不同:

ADO ProviderLINQ to SQL API LINQ to SQL Provider



                                                                             


                     

四:DataContext

DataContext的目的是转换你的请求的对象为SQL查询影响数据库,并且,这里DataContext受权LINQ实现Standard Query Operators,LINQ to SQL是翻译查询为SQL语句返回服务端.
在上一篇中我们谈过LINQ to SQL的对象模型,里面知道DataContext对应的就是数据库,主要原因就是DataContext同过设置连接字符串参数后就能连接到数据库.而我们又将数据库中的表和关系通过ORM生成对象放在内存(标识放在内存)中.


其中使用DataContext最基本的方式是:

None.gif DataContext db  =   new  DataContext(
None.gif
" Initial Catalog=AdventureWorks;Integrated i
None.gif
Security = sspi " );


如果你要先了解DataContext你可以先使用LINQ to SQL provieder生成.dbml文件,查看里面.cs文件.你就能看见DataContext的一些使用.
None.gif [System.Data.Linq.Mapping.DatabaseAttribute(Name = " Northwind " )]
None.gif
public   partial   class  VLinqDataClassesDataContext : System.Data.Linq.DataContext
ExpandedBlockStart.gifContractedBlock.gif    
dot.gif {
InBlock.gif        
InBlock.gif        
private static System.Data.Linq.Mapping.MappingSource mappingSource = new AttributeMappingSource();
InBlock.gif
public VLinqDataClassesDataContext() :
InBlock.gif                
base(global::CSharpLanguage_C_app.Properties.Settings.Default.NorthwindConnectionString, mappingSource)
ExpandedSubBlockStart.gifContractedSubBlock.gif        
dot.gif{
InBlock.gif            OnCreated();
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        
public VLinqDataClassesDataContext(string connection) :
InBlock.gif                
base(connection, mappingSource)
ExpandedSubBlockStart.gifContractedSubBlock.gif        
dot.gif{
InBlock.gif            OnCreated();
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        
public VLinqDataClassesDataContext(System.Data.IDbConnection connection) :
InBlock.gif                
base(connection, mappingSource)
ExpandedSubBlockStart.gifContractedSubBlock.gif        
dot.gif{
InBlock.gif            OnCreated();
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        
public VLinqDataClassesDataContext(string connection, System.Data.Linq.Mapping.MappingSource mappingSource) :
InBlock.gif                
base(connection, mappingSource)
ExpandedSubBlockStart.gifContractedSubBlock.gif        
dot.gif{
InBlock.gif            OnCreated();
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        
public VLinqDataClassesDataContext(System.Data.IDbConnection connection, System.Data.Linq.Mapping.MappingSource mappingSource) :                 
InBlock.gif
base(connection, mappingSource)
ExpandedSubBlockStart.gifContractedSubBlock.gif        
dot.gif{
InBlock.gif            OnCreated();
ExpandedSubBlockEnd.gif        }

ExpandedBlockEnd.gif}

可以看出DataContext有多个重载,我们可以很清楚的看见它的几个被重载的函数;


你能通过一个IDbConnection(表示打开连接数据源).IDbConncetion是一个定义在System.Data.命名空间的接口,允许继承这个接口实现一个Conncetion类,包括一个唯一的访问数据源的Session.这样做的好处就是应用程序不要立刻创建一个IDbConncetion的实例.而是创建的是一个继承它的类的实例.(现在已经解释两个拉!).
这一个:

mappingSource是表示一个mapping信息,是绘制CLR对象到entities.它有两个方法CreateModel方法和GetModel方法,GreateModel方法是用来,返回一个匹配当恰mapping schema所创建的meta-model.GetModel方法就是返回一个meta-model.meta-model是表示数据库和domain object(域对象)之间的映射的一个抽象(就是他们之间的描述资源).就是有CLR type system 和 SQL database之间的信息.你可以从这个类中得到用户在数据库中自定义的函数,得到从数据库表中得到的columns映射到domain object的类型,还有数据库中的表名等相关信息.还有AttributeMappingSource是继承MappingSource类,它是在context中的attributes去创建一个mapping model.

来看都使用怎样得到的
//强类型的dataContext就自己写拉!
None.gif Northwnd nw  =   new  Northwnd();
None.gifvar model 
=   new  AttributeMappingSource().GetModel( typeof (Northwind));
None.gif
None.gif        
foreach  (var mt  in  model.GetTables())
None.gif
None.gif            Console.WriteLine(mt.TableName);
None.gif
None.gifvar model2 
=  nw.Mapping;
None.gif            
foreach  (var mt2  in  model2.GetTables())
ExpandedBlockStart.gifContractedBlock.gif            
dot.gif {
InBlock.gif                Console.WriteLine(mt2.TableName);
ExpandedBlockEnd.gif            }

None.gif            Console.ReadLine();

            到现在都没有使用DataContext,但我们却能找到DataContext中Mapping数据库后进入.NET 系统的相关信息

          
None.gif var model3  =   new  AttributeMappingSource().GetModel( typeof (Northwnd));
None.gif            
foreach  (var mt3  in  model3.GetTables())
ExpandedBlockStart.gifContractedBlock.gif            
dot.gif {
InBlock.gif                Console.WriteLine(mt3.TableName);
InBlock.gif                
foreach (var dm in mt3.RowType.DataMembers)
ExpandedSubBlockStart.gifContractedSubBlock.gif                
dot.gif{
InBlock.gif                    Console.WriteLine(
"Column{0}",dm.MappedName);
InBlock.gif                    Console.WriteLine(dm.AutoSync);
InBlock.gif                    Console.WriteLine(dm.CanBeNull);
InBlock.gif                    
//Console.WriteLine(dm.DeferredValueAccessor.Type);
InBlock.gif                    
//Console.WriteLine(dm.DeferredSourceAccessor.Type);
InBlock.gif
                    Console.WriteLine(dm.UpdateCheck);
InBlock.gif                    Console.WriteLine(dm.Member.MemberType);
InBlock.gif                    Console.WriteLine(dm.IsPrimaryKey);
InBlock.gif                    Console.WriteLine(dm.IsDiscriminator);
InBlock.gif                    Console.WriteLine(dm.IsDeferred);
InBlock.gif
InBlock.gif
InBlock.gif                    
//Console.WriteLine(dm.Association.IsMany);
InBlock.gif                    
//Console.WriteLine(dm.Association.OtherKey);
InBlock.gif                    
//Console.WriteLine(dm.Association.ThisKeyIsPrimaryKey);
InBlock.gif                    
//Console.WriteLine(dm.Association.ThisKey);
InBlock.gif                    
//Console.WriteLine(dm.Association.IsForeignKey);
InBlock.gif                    
//Console.WriteLine(dm.Association.DeleteRule);
ExpandedSubBlockEnd.gif
                }

ExpandedBlockEnd.gif            }

None.gif            Console.ReadLine();

所以可以看出在第三种重载中参数就是一个连接字符串和一个Mapping资源描述,就能找回数据.其他两种就是他们的结合.

五:DataContext的成员


在本篇中对DataContext的成员的介绍如果和删除,修改就放在以后的文章中谈,还有和性能有关的我们放在性能的文章中来谈,所以就只有下面几个方法和属性拉.如果你还要对DataContext深入的研究,你可以到这一篇文章中,这里谈的是 domain model(帅哥"martin Fowler")的应用.


(1)GetTable(TEntity)泛型方法


public Table<TEntity> GetTable<TEntity>() where TEntity : class

返回通过TEntity指定类型的有详细类型的对象集合.这里分直接实例DataContext是:

None.gif
None.gif DataContext dbContext 
=   new  DataContext( " Data Source=localhost;Initial Catalog=Northwind;Integrated Security=true; " );
None.gifTable
< customer >  customerTable  =  dbContext.GetTable < customer > ();


而强类型的DataContext这个方法就被封装                  

None.gif public   partial   class  Northwnd : DataContext
ExpandedBlockStart.gifContractedBlock.gif    
dot.gif {
InBlock.gif
InBlock.gif        
private static MappingSource mappingSource = new AttributeMappingSource();
InBlock.gif
ExpandedSubBlockStart.gifContractedSubBlock.gif        
public Northwnd() : base(global::CSharpLanguage_C_app.Properties.Settings.Default.NorthwindConnectionString, mappingSource) dot.gif{ }
InBlock.gif
InBlock.gif        
public Table<customer> Customers
ExpandedSubBlockStart.gifContractedSubBlock.gif        
dot.gif{
InBlock.gif            
get
ExpandedSubBlockStart.gifContractedSubBlock.gif            
dot.gif{
InBlock.gif                
return this.GetTable<customer>();
ExpandedSubBlockEnd.gif            }

ExpandedSubBlockEnd.gif        }

ExpandedBlockEnd.gif   }

它还有一个弱类型的GetTable(Type)方法;是一个相关动态查询.反射一个泛型方法做为参数.

None.gif public  ITable GetTable(
None.gif    Type type
None.gif)


这个以后到LINQ Dynamic部分我再关注.(可以看我翻译的 这篇和这 )




(2)DataContext.CreateDatabase方法:
能在服务端创建一个数据库.
在几种情况下你会使用上它:
  1. 你需要构建一个应用程序动态安装在客户系统中.
  2. 你构建一个客户端应用程序需要保存数据在本数据库中保持离线状态.

在使用前你需要使用attributes对你的实体做出描述,后再使用.

(3)DatabaseExists方法
确定相应的数据库是否被打开.是通过使用Connection 属性去打开相应的数据库.

(3)deleteDatabase
删除相应的数据库

None.gif string  userTempFolder  =  Environment.GetEnvironmentVariable( " Temp " );
None.gif            
string  userMDF  =  System.IO.Path.Combine(userTempFolder,  @" Northwind " );
None.gif
None.gif            Northwnd newBb 
=   new  Northwnd(userMDF);
None.gif
None.gif            
if  (newBb.DatabaseExists())
ExpandedBlockStart.gifContractedBlock.gif            
dot.gif {
InBlock.gif                Console.WriteLine(
"CreateDB DB exists");
InBlock.gif                newBb.DeleteDatabase();
ExpandedBlockEnd.gif            }

None.gif            
else
ExpandedBlockStart.gifContractedBlock.gif            
dot.gif {
InBlock.gif                Console.WriteLine(
"Delete DB does not exist");
InBlock.gif                newBb.CreateDatabase();
ExpandedBlockEnd.gif            }



(4)Log Property


可以将SQL命令的输出写到到指定文件中,主要我们是通过重写输出对象来做到的.(这里很灵活)
1:输出到
None.gif Debugger  window:    context.Log  =   new  DebuggerWriter();

2:在页面上输出SQL语句可以在这里 下载:

3:将LOG里面输出的内容写到一个文本里面:

None.gif  StreamWriter writer  =   new  StreamWriter(HttpContext.Current.Request.PhysicalApplicationPath  +   " DataContextLog.txt " true );
None.gif DataContext.Log 
=  writer;

有很多方式.



(5)Connection属性


返回一个Connection.

还有更高级的部分在 DataContext的讨论(1)会谈到。


worksguo
www.cnblogs.com




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值