我在 vb.net 中做 windows 应用程序。我有客户对象包含保存方法。我如何生成插入查询?
我需要将对象保存在关系数据库(SQL 服务器)中。我需要知道哪种是插入的正确方法,即。在 save 方法中,我编写了 SQL 语句来保存对象。这是正确的方法吗?
谢谢
我在 vb.net 中做 windows 应用程序。我有客户对象包含保存方法。我如何生成插入查询?
我需要将对象保存在关系数据库(SQL 服务器)中。我需要知道哪种是插入的正确方法,即。在 save 方法中,我编写了 SQL 语句来保存对象。这是正确的方法吗?
谢谢
SQL 的简单 INSERT 语句采用以下基本形式:
INSERT INTO [tablename] ( [column1], [column2], ... ) VALUES ( [value1], [value2], ...)
因此,我们显然需要了解您正在使用的数据库表:它有哪些列。我们还需要了解这个类:它有什么属性。最后,我们需要了解表列和类属性的数据类型,以及属性如何映射到列。对于非常简单的对象,名称和类型将对齐。但在其他情况下,您的类本身可能包含一个(或多个)集合,这意味着将数据插入多个表中。
确定了这一切之后,我们仍然需要两件事:数据库的连接信息(通常被提炼成单个连接字符串)以及您是否担心您的类实例之前可能已保存,在这种情况下您想要构建一个 UPDATE 语句而不是 INSERT。
假设您可以以令人满意的方式回答所有这些问题,您的 VB.Net 代码将如下所示(当然,在适当的情况下替换您的特定列、属性、类型和连接信息):
Public Class Customer
Public Sub Save()
DAL.SaveCustomer(Me)
End Sub
' ...'
End Class
.
' a VB Module is a C# static class'
Public Module DAL
Private ConnString As String = "Your connection string here"
Public Sub SaveCustomer(ByVal TheCustomer As Customer)
Dim sql As String = "" & _
"INSERT INTO [MyTable] (" & _
"[column1], [column2], ..." & _
") VALUES (" & _
"@Column1, @Column2, ... )"
Using cn As New SqlConnection(ConnString), _
cmd As New SqlCommand(sql, cn)
cmd.Parameters.Add("@column1", SqlDbTypes.VarChar, 50).Value = TheCustomer.Property1
cmd.Parameters.Add("@column2", SqlDbTypes.VarChar, 1000).Value = TheCustomer.Property2
cn.Open()
cmd.ExecuteNonQuery()
End Using
End Sub
End Module
我知道您已经听说分离出您的数据库代码是“正确的做法”tm,但我认为您可能还想要一些更具体的原因来说明您希望以这种方式构建代码的原因:
这里有几个问题。首先,你到底在哪里保存这个?您说 SQL,但它是 SQL Server、SQL Express 的实例、本地数据缓存 (SQL CE 3.5) 还是通过 Web 服务保存以与您的 SQL SERVER 对话。这些不同的数据源具有不同的连接选项/要求,并且在 SQL CE 的情况下,SQL 本身还涉及一些其他“陷阱”。
其次,您确定要将数据保存到 SQL Server 等关系数据存储中吗?考虑一下,您可以改用 XML、数据文件(文本、CSV 等)甚至自定义二进制文件类型。
由于您正在使用 Windows 应用程序,因此您可以选择在何处以及如何保存数据。在您知道要将数据放在哪里之前,我们很难帮助您这样做。
我同意迈克霍弗的观点。将您的对象检索和持久化的类与您的业务类分开是拥有灵活和健壮设计的关键。这是您希望在 GUI 或业务层中看到的那种代码:
//Populate Customer Objects List with data
IList<Customer> customerList = new List<Customer>()
Customer newCustomer1 = new Customer();
newCustomer.Name = "New Name"
newCustomer.email ="abcd@abcd.com"
customerList.Add(newCustomer1)
//DAL calls
DataAccessClass dalClass = new DataAccessClass ();
dalClass.InsertCustomers(customerList);
在您的 DALClass 中应该有一个名为 InsertCustomers(IList customers) 的方法,它应该具有以下代码:
Public Function InsertCustomers(ByVal objectList As IList(Of Customer)) As Integer
Dim command As IDbCommand = Nothing
Dim rowsAffected As Integer = 0
Dim connection As IDbConnection = New System.Data.SqlClient.SqlConnection(Me.ConnectionString)
Try
connection.Open
Dim e As IEnumerator = objectList.GetEnumerator
Do While e.MoveNext
command = connection.CreateCommand
command.CommandText = "insert into dbo.Customer(CustomerID,CustomerGUID,RegisterDate,Password,SiteID,Las"& _
"tName,FirstName,Email,Notes,BillingEqualsShipping,BillingLastName) values (@Cust"& _
"omerID,@CustomerGUID,@RegisterDate,@Password,@SiteID,@LastName,@FirstName,@Email"& _
",@Notes,@BillingEqualsShipping,@BillingLastName)"
System.Console.WriteLine("Executing Query: {0}", command.CommandText)
Dim paramCustomerID As IDbDataParameter = command.CreateParameter
paramCustomerID.ParameterName = "@CustomerID"
command.Parameters.Add(paramCustomerID)
Dim paramCustomerGUID As IDbDataParameter = command.CreateParameter
paramCustomerGUID.ParameterName = "@CustomerGUID"
command.Parameters.Add(paramCustomerGUID)
Dim paramRegisterDate As IDbDataParameter = command.CreateParameter
paramRegisterDate.ParameterName = "@RegisterDate"
command.Parameters.Add(paramRegisterDate)
Dim paramPassword As IDbDataParameter = command.CreateParameter
paramPassword.ParameterName = "@Password"
command.Parameters.Add(paramPassword)
Dim paramSiteID As IDbDataParameter = command.CreateParameter
paramSiteID.ParameterName = "@SiteID"
command.Parameters.Add(paramSiteID)
Dim paramLastName As IDbDataParameter = command.CreateParameter
paramLastName.ParameterName = "@LastName"
command.Parameters.Add(paramLastName)
Dim paramFirstName As IDbDataParameter = command.CreateParameter
paramFirstName.ParameterName = "@FirstName"
command.Parameters.Add(paramFirstName)
Dim paramEmail As IDbDataParameter = command.CreateParameter
paramEmail.ParameterName = "@Email"
command.Parameters.Add(paramEmail)
Dim paramNotes As IDbDataParameter = command.CreateParameter
paramNotes.ParameterName = "@Notes"
command.Parameters.Add(paramNotes)
Dim paramBillingEqualsShipping As IDbDataParameter = command.CreateParameter
paramBillingEqualsShipping.ParameterName = "@BillingEqualsShipping"
command.Parameters.Add(paramBillingEqualsShipping)
Dim paramBillingLastName As IDbDataParameter = command.CreateParameter
paramBillingLastName.ParameterName = "@BillingLastName"
command.Parameters.Add(paramBillingLastName)
Dim modelObject As Customer = CType(e.Current,Customer)
paramCustomerID.Value = modelObject.CustomerID
paramCustomerGUID.Value = modelObject.CustomerGUID
paramRegisterDate.Value = modelObject.RegisterDate
If IsNothing(modelObject.Password) Then
paramPassword.Value = System.DBNull.Value
Else
paramPassword.Value = modelObject.Password
End If
paramSiteID.Value = modelObject.SiteID
If IsNothing(modelObject.LastName) Then
paramLastName.Value = System.DBNull.Value
Else
paramLastName.Value = modelObject.LastName
End If
If IsNothing(modelObject.FirstName) Then
paramFirstName.Value = System.DBNull.Value
Else
paramFirstName.Value = modelObject.FirstName
End If
If IsNothing(modelObject.Email) Then
paramEmail.Value = System.DBNull.Value
Else
paramEmail.Value = modelObject.Email
End If
If IsNothing(modelObject.Notes) Then
paramNotes.Value = System.DBNull.Value
Else
paramNotes.Value = modelObject.Notes
End If
paramBillingEqualsShipping.Value = modelObject.BillingEqualsShipping
If IsNothing(modelObject.BillingLastName) Then
paramBillingLastName.Value = System.DBNull.Value
Else
paramBillingLastName.Value = modelObject.BillingLastName
End If
rowsAffected = (rowsAffected + command.ExecuteNonQuery)
Loop
Finally
connection.Close
CType(connection,System.IDisposable).Dispose
End Try
Return rowsAffected
End Function
手动编写 DAL 代码很痛苦,但是您将完全控制您的 DAL、SQL 和映射代码,并且将来更改其中任何一个都将变得轻而易举。
如果您不想手动编写所有 DAL 代码,您可以使用像Orasis Mapping Studio这样的 CodeGenerator来生成与所示完全相同的代码,而无需编写任何内容。您只需要在工具中构建 SQL,将属性映射到参数即可。它将为您生成所有其余部分。
祝你好运,快乐的 DAL 编码!
我和斯蒂芬·赖顿在一起。这里有很多变数,还有很多悬而未决的问题。如果是 SQL,它甚至是 SQL 的 Microsoft 方言吗?是甲骨文吗?MySQL?还有什么?
无论如何,我个人的偏好是尽可能避免在应用程序中构建 SQL,并调用存储过程,即使对于插入和更新也是如此。然后我将过程的参数传递给 ADO.NET 命令对象。我脑子里有一个疯狂的想法,即 SQL 属于数据库。也许这来自于我在互联网时代花费大量时间调试将 SQL 字符串拼接在一起的可怕编写的 ASP 代码。(再也不。)
如果您觉得绝对有必要这样做,请参阅System.Text.StringBuilder类。学习它。爱它。让它成为你最好的朋友。
更新: 看到您的回复,我现在看到您正在使用 SQL Server。这让事情变得更好。
我建议将您的 SQL 代码分离到一个单独的类中,远离实际的业务类。有些人可能不同意这一点,但它会使课程的目的保持清晰。(请参阅关注点分离。)
您希望让您的业务对象处理业务逻辑,以及一个单独的类来处理将数据输入和输出数据库的工作。这样,如果您对序列化逻辑有疑问,您就可以更好地了解在哪里查找,并且大大减少了处理业务逻辑的机会。它还使您的应用程序更容易理解。
多写几门课的一点前期努力会在未来获得巨大的回报。
但那只是我的个人意见。
我更喜欢 Mike Hofer 的想法,在 SQL Server 端有一个存储过程来处理实际的数据更新,并有一个单独的类来包装对这些存储过程的调用。只是我的 0.02 美元
不太确定OP在问什么。
您需要在“保存”方法中准确定义您在做什么
“保存”方法通常意味着这两种情况都由程序处理。
更好的方法是使用 ("Create" or "Insert") 和 ("Update" or "Save") 方法。
或者也许有一个程序可以同时处理这两种情况。