实验营 1: Linq To Sql: 集成数据库语言查询
这个实验营将向您清晰地描绘借助于 Linq to Sql,Linq 项目对于关系型数据存取的支持。 您将先创建一个基于 Northwind 数据库的对象模型,随后使用新的VB.NET 查询表达式查询 Northwind 数据库。
我们将使用 Linq to Sql 设计器,从已有数据库中创建一个对象模型。而后,将着眼于映射表之间的实体关系,并且使用创建,更新与删除操作。紧接着,我们将探索如何使用事务,对象检索(retrieval)技术,存储过程集成与使用 Linq to Sql 标识对象 (identify)。
Linq to Sql 是一个语言无关的 Linq 项目组件。虽然为了一致性,这个文档中的例子全都用 Visual Basic 来展示,但 Linq to Sql 还是可以在支持 Linq 版本的C# 编译器中正常使用。
Linq 项目依赖许多内建于 VB.Net中的新的关键字和语法,并且当前它们已被集成于 Microsoft Visual Studio 2008 Beta 2 之中。它将带给我们使用新IDE特性的机会,例如集成调试器,IntelliSense™(智能感知),以及编译时语法检查。
实验营目标
预估完成这次动手实验营的时间:60 分钟
这个实验营的目标是实践并学习有关Linq to SQL 与 VB.NET 程序集成的一些任务。我们将带您探索“CRUD ”操作——创建,接收,更新与删除,以及它们怎样在不使用外部方法的情况下完成 SQL查询或更新命令。您将获取程序中的实体如何映射至数据库表,以及怎样调节映射过程。
练习1 – 利用代码生成器建立对象模型
练习2 – 创建你的第一个 Linq to SQL 项目
练习3 – 创建一个对象模型
练习4 – 修改数据库中的数据
练习5 – 运用更高级的特性
练习1 – 利用代码生成器建立对象模型
在这个练习中我们将看到如何透过可视化的 Linq 设计器简单地制作一个对象模型。下两个练习将深入研究在幕后究竟发生了什么:但是设计器已经为您完成了这一切!
步骤 1 – 创建一个 Linq 项目
1. 单击 开始 | 程序 | Microsoft Visual Studio 2008 Beta 2 | Microsoft Visual Studio 2008 Beta 2 菜单命令。
2. 打开 Microsoft Visual Studio 后,单击 File | New | Project… 菜单命令
3. 在 New Project 对话框中的 Project types 中,单击Other Languages | Visual Basic
4. 在对话框右侧的 Templates 中,选择 Console Application
5. 在 Name 字段中填写 “Linq To Sql VB”为您的解决方案提供一个名字
6. 单击 OK
步骤 2 – 增加一个引用到System.Data.Linq程序集
1. 在 Microsoft Visual Studio中,单击 Project | Add Reference… 菜单命令
2. 打开 Add Reference 对话框,确保 .NET 标签已被选择
3. 选取System.Data.Linq 程序集
4. 点击OK
在Module1.vb 中引入命名空间 System.Data.Linq ,切记放置于模块定义之前:
Imports System.Data.Linq
步骤 3 – 创建一个 Linq to Sql 文件
1. 在 Microsoft Visual Studio中,单击 Project | Add New Item… 菜单命令
2. 点击右侧Templates 窗口中的Linq To Sql File
3. 为这个新项提供一个名字,在Name字段中输入“Northwind”
4. 点击OK
步骤 4 – 增加一个新的数据连接
1. 在Microsoft Visual Studio中,点击 View | Server Explorer 菜单命令 (或者按下 Ctrl+W,L)
2. 在Server Explorer 窗口中点击 Connect to database 按钮
3. 弹出的 Add Connection 对话框中,在Server name 字段中输入“."sqlexpress”,提供本地数据库服务器地址
4. 使用Select or enter a database name 组合框,更改数据库为 “Northwind”
5. 点击OK
步骤 5 – 创建你的对象模型
1. 打开 Data Connections树视图
2. 展开 Northwind文件夹
3. 展开 Tables文件夹
4. 在 solution explorer 中双击打开 Northwind.dbml 文件
5. 从 table 文件夹拖拽 Customers表到 Linq to SQL 设计器
6. 从 table 文件夹拖拽Orders表到 Linq to SQL 设计器
7. 从 table 文件夹拖拽 Employees表到 Linq to SQL 设计器
步骤 6 – 查询你的对象模型
1. 按下 F5以调试你的程序
正如你所看到的,设计器为你写下了所有的“plumbing”代码。你的主程序果然运行正常!
步骤 7 – 映射一个存储过程
我们已经学会怎样从表映射到对象,以及如何声明两个表之间的关联。现在我们正希望让您了解怎样映射一个数据库中的存储过程到我们的对象模型。
1. 打开 Data Connections 树视图
2. 展开 Northwind 文件夹
3. 展开 Stored Procedures文件夹
4. 在 solution explorer 中双击打开 Northwind.dbml 文件
5. 从 Stored Procedures文件夹拖拽Ten Most Expensive Products到设计器
6. 对您的程序中的 Main 方法作出下列修改,使用从设计器创建的对象模型。
Sub Main()
'如果我们在设计器中保存了连接字符串,那么将不再需要提供连接字符串。
Dim db As New NorthwindDataContext()
Dim q = From customer In db.Customers _
Where customer.Region = Nothing _
Select customer.ContactName
For Each cust In q
Console.WriteLine(cust)
Next
Console.ReadLine()
End Sub
7. 按下F5以调试这个程序
当你输入了这段代码,注意他是这么工作的,在 IDE 中, IntelliSense将会把你的映射后的存储过程 Ten_Most_Expensive_Products显示为一个强类型的 DataContext 中的一个设计器生成的方法。同样提示你的,还包括设计器生成的类型Ten_Most_Expensive_Product 包含两个强类型的属性,它们映射从存储过程返回的字段。注意,如果你复制并粘贴上面的代码:简单地输入“p.”来观察我们谈论的话题。
步骤 8 – 检索新的结果集
迄今为止我们已经运行了能够接受完整对象的查询。但是我们也可以只查询需要的属性,您也可能需要创建复合的查询。在 Traditional SQL 中,含有任意列的集合都可以作为结果集返回。在 Linq to Sql,您可以透过使用匿名类型完成这类任务。
1. 修改Main方法中的代码,用于创建一个仅仅接收 ContactName 属性的查询并显示:
Sub Main()
'如果我们在设计器中保存了连接字符串,那么将不再需要提供连接字符串。
Dim db As New NorthwindDataContext()
Dim q = From customer In db.Customers _
Where customer.Region = Nothing _
Select Company = customer.CompanyName, _
Contact = customer.ContactName
For Each cust In q
Console.WriteLine("{0}/{1}", cust.Contact, cust.Company)
Next
Console.ReadLine()
End Sub
2. 再次修改这些代码,用于创建一个新的包含我们想得到数据的对象,而后进行输出:
Sub Main()
'如果我们在设计器中保存了连接字符串,那么将不再需要提供连接字符串。
Dim db As New NorthwindDataContext()
Dim ids = From customer In db.Customers _
From emp In db.Employees _
Where customer.City = emp.City _
Select emp.EmployeeID _
Distinct
For Each id In ids
Console.WriteLine(id)
Next
Console.ReadLine()
End Sub
Sub Main()
'如果我们在设计器中保存了连接字符串,那么将不再需要提供连接字符串。
Dim db As New NorthwindDataContext()
Dim ids = From customer In db.Customers _
From emp In db.Employees _
Where customer.City = emp.City _
Select emp.EmployeeID _
Distinct
For Each id In ids
Console.WriteLine(id)
Next
Console.ReadLine()
End Sub
3. 按下F5以调试这个程序
请注意这个操作符运行时没有相应的类型名称。原因是编译器将基于选择列的名称与类型,创建一个新的匿名类型。您同样需要注意,匿名类型中的成员已经被重命名为Company 与 Contact。指定名称是可选的,默认行为将把它命名为与映射对象中的源字段名称一致。最后,当 For Each 语法执行时,一个新类型的实例引用与它的所有类型将可以被访问。
4. 更改这些文档,完成一项 Join 操作:
Sub Main()
'如果我们在设计器中保存了连接字符串,那么将不再需要提供连接字符串。
Dim db As New NorthwindDataContext()
Dim ids = From customer In db.Customers _
From emp In db.Employees _
Where customer.City = emp.City _
Select emp.EmployeeID _
Distinct
For Each id In ids
Console.WriteLine(id)
Next
Console.ReadLine()
End Sub
5. 按下F5以调试整个解决方案
上述示例阐明了当没有显式关联可以导航的情况下,一个 SQL 样式的 Join 同样可以被使用。它同样展示了可以仅选定单个特别的属性可以代替整个对象被发送到程序中。
上面是vb写的。
下面是一个简单的DLINQ代码:获得 pubs 数据库 authors 表的所有作者的 au_id 信息。
using System;
using System.Linq;
using System.Data.Linq; // 这个命名空间在单独的组件 System.Data.Linq.dll 中
public class DLinqTest
{
public static void DoSomeThing()
{
// 链接字符串
string connectionString = "Data Source=192.168.5.2;Initial Catalog=pubs;Persist Security Info=True;User ID=sa;Password=******";
// 我们就是通过使用 DataContext 来 DLINQ链接数据库的。
DataContext db = new DataContext(connectionString);
Table<Authors> authors = db.GetTable<Authors>();
var users = from a in authors orderby a.au_id select a;
foreach (var a in users)
{
Console.WriteLine(a.au_id);
}
}
}
// 数据库中的表结构影射的实体对象,注意其中的 Attribute.
[Table(Name = "authors")]
public class Authors
{
[Column(IsPrimaryKey = true)]
public string au_id { get; set; }
[Column]
public string au_lname { get; set; }
[Column]
public string au_fname { get; set; }
[Column]
public string phone { get; set; }
[Column]
public string city { get; set; }
[Column]
public string state { get; set; }
[Column]
public string zip { get; set; }
[Column]
public bool contract { get; set; }
}
DLINQ 链接到数据库的步骤:
1、创建数据表跟实体对应的实体类(字段和元素可以不一一对应),并把这个类标上Table 特性,根数据表字段有关的元素标上Column特性;
2、使用 DataContext 和数据库链接字符串建立跟数据库的链接,然后使用 DataContext 的实例的 GetTable 方法获得对应表影射的实体类。
XLINQ 访问 XML 文件的方法
XLINQ 的例子我们就写稍稍复杂点,通过获得我(蝈蝈俊)博客的RSS,然后把RSS中的链接和标题打印出来:
下面就是这个功能的演示代码:
using System;
using System.Linq;
using System.Xml.Linq;
public class XLINQ
{
public static void DoSomeThing()
{
XElement feed = XElement.Load("http://blog.joycode.com/ghj/Rss.aspx");
if (feed.Element("channel") == null)
return;
var rss = from item in feed.Element("channel").Elements("item")
select new
{
title = item.Element("title").Value,
link = item.Element("link").Value
};
foreach (var item in rss)
{
Console.WriteLine(item.link);
Console.WriteLine(item.title);
Console.WriteLine("*****");
}
}
}
XLINQ 加载数据的核心就在于 XElement.Load
另外,上述代码中使用了匿名类型,不知道大家还记不得我前几篇博客设计到的这个知识点。