thongkorn โพสต์ 2017-10-28 13:00:22

[VB.NET] พื้นฐานการสร้าง Primary Key ขึ้นมาใหม่ โดยไม่ให้ซ้ำกับค่าเดิม

http://www.g2gnet.com/webboard/images/vbnet/NewPrimaryKey.png
มาทำความเข้าใจกับ Primary Key และ Identifier ...
Primary Key (PK) หรือกุญแจหลัก เป็นคีย์ที่มีความเป็นเอกลักษณ์โดยเฉพาะ (Unique) โดยต้องไม่ซ้ำกับข้อมูลในรายการแถวอื่นๆ และที่สำคัญอีกอย่างคือ มันจะเปลี่ยนแปลงค่าไม่ได้ เพราะหากเปลี่ยนค่าได้ มันจะมีผลกระทบต่อความสัมพันธ์ในตาราง (Table) อื่นๆ ... ตามตำราโดยทั่วไป เขามักจะนิยมเอา Primary Key (PK) และ Identifier (ID) มาเป็นตัวเดียวกัน ก็เพื่อให้ง่ายต่อการนำมาสอนหรืออธิบาย เช่น รหัสบัตรประชาชน หรือ รหัสประกันสังคม เพราะจากคำนิยามค่าต่างๆเหล่านี้ มันก็มีค่าโดยเฉพาะ ซึ่งจะซ้ำกันไม่ได้อยู่แล้วตามหลักวิชาการ แต่ทว่าในความเป็นจริงนั้น มันจะต้องถูกแยกออกจากกัน โดยที่ ...

- Primary Key หรือ PK ควรจะเป็นตัวเลขแบบชนิดจำนวนเต็ม เพราะคำนวณหาค่าได้ง่าย ซึ่งจะ มีค่าที่ซ้ำกันไม่ได้ และเปลี่ยนแปลงค่าไม่ได้ เพราะค่า Primary Key จะเป็นตัวเชื่อมโยงไปสร้างความสัมพันธ์กับตารางอื่นๆ ซึ่งโปรแกรมเมอร์จะต้องใช้ PK นี้ในการกำหนดและควบคุมการทำงานของโปรแกรม

- IDentifier หรือ ID ค่านี้จะเป็นค่าที่บ่งบอกเอกลักษณ์โดยเฉพาะ (เหมือนกันกับ PK) ซึ่งจะ มีค่าที่ซ้ำกันไม่ได้ แต่สามารถเปลี่ยนแปลงค่าได้ ค่า ID มักจะผสมตัวเลข ตัวอักษร หรือตัวเลขอย่างเดียว เช่น รหัสสินค้า รหัสนักศึกษา ฯลฯ ... โดยค่า ID นี้ Users จะเป็นผู้ใช้งาน ดังนั้นการที่มันต้องสามารถเปลี่ยนค่า ID ได้ หลักๆมาจากข้อมูลอินพุทที่ผิดพลาด หรือเกิด Human Error เองของผู้ใช้งาน ซึ่งเมื่อเกิดการเปลี่ยนแปลงค่า ID ไป จะไม่มีผลกระทบใดๆต่อระบบเลย นั่นก็เพราะว่าค่า Primary Key (PK) ต่างหาก ที่จะเป็นตัวยึดโยงความสัมพันธ์ต่างๆของตารางข้อมูลเอาไว้ ...

บทความนี้เราจะมาว่ากันเรื่อง การสร้าง Primary Key ใหม่ โดยไม่ให้ซ้ำกันกับค่าเดิมเลย แอดมินไม่แนะนำให้ใช้การสร้าง Primary Key ในแบบ Autonumber จากฐานข้อมูล เพราะอาจจะมีปัญหาในการนำไปใช้งานแบบมัลติยูสเซอร์ หรือหากต้องการจะย้ายระบบฐานข้อมูล ก็อาจจะเกิดความยุ่งยากขึ้นได้ ...

สิ่งที่คุณจะได้รู้ ...
- การสร้าง Primary Key โดยไม่ให้ซ้ำกัน
- การใช้ฟังค์ชั่นที่แอดมินสร้างขึ้นเอง SetupNewPK หรือ DoSQL ซึ่งฟังค์ชั่นทั้ง 2 ตัวนี้ เป็นการลดความซ้ำซ้อนในปฏิบัติการกับฐานข้อมูล เรียกได้ว่าเขียนครั้งเดียวแต่นำไปใช้ได้เหมือนกันหมดทุกฟอร์ม
- วิธีการลบข้อมูล

ทุกๆโปรเจคเราเริ่มต้นด้วยการค้นคืนข้อมูล หรือ Retrieve (ตัวอย่างนี้ใช้แบบ Bound Data)
    ' / --------------------------------------------------------------------------------
    ' / Data retrieval.
    Private Sub RetrieveData()
      strSQL = "SELECT tblContact.ContactPK, tblContact.Fullname FROM tblContact ORDER BY ContactPK"
      Try
            If Conn.State = ConnectionState.Closed Then Conn.Open()
            Dim Cmd As OleDbCommand = New OleDbCommand(strSQL, Conn)
            Dim Reader As OleDb.OleDbDataReader = Cmd.ExecuteReader
            Dim DT As New DataTable
            DT.Load(Reader)
            dgvData.DataSource = DT
            DT.Dispose()

      Catch ex As Exception
            MessageBox.Show(ex.Message)
      End Try
    End Sub
ฟังค์ชั่นในการสร้างค่า Primary Key (SetupNewPK) ...
    ' / --------------------------------------------------------------------------------
    ' / Function to find and create the new Primary Key not to duplicate.
    Function SetupNewPK(ByVal sql As String) As Long
      If Conn.State = ConnectionState.Closed Then Conn.Open()
      Dim Cmd As New OleDbCommand(sql, Conn)
      '/ Check if the information is available. And return it back
      If IsDBNull(Cmd.ExecuteScalar) Then
            '// Start at 1
            SetupNewPK = 1
      Else
            SetupNewPK = Cmd.ExecuteScalar + 1
      End If
    End Functionเราใช้การหาค่าสูงสุดของ Primary Key ตัวเดิมด้วย MAX(tblContact.ContactPK) AS MaxPK
หาก IsDBNull(Cmd.ExecuteScalar) ไม่มีค่าใดๆอยู่เลย แสดงว่าเป็นตารางข้อมูลว่างเปล่า ก็กำหนดค่าใหม่เป็น 1 แต่ถ้าหากไม่ใช่ก็บวกเพิ่มขึ้น 1

ฟังค์ชั่นในการปฏิบัติการกับฐานข้อมูล (DoSQL) ... ไม่ว่าคุณจะเพิ่ม แก้ไข หรือลบ สามารถใช้ฟังค์ชั่นนี้ได้เลย
    ' / --------------------------------------------------------------------------------
    ' / Function to Execute data. (Add, Edit, Delete) ... Common base in your program.
    Private Function DoSQL(ByVal Sql As String) As Boolean
      Dim Cmd As New OleDbCommand
      If Conn.State = ConnectionState.Closed Then Conn.Open()
      'MsgBox(Sql)
      Try
            Cmd.Connection = Conn
            Cmd.CommandType = CommandType.Text
            Cmd.CommandText = Sql
            Cmd.ExecuteNonQuery()
            Cmd.Dispose()
            Return True
      Catch ex As Exception
            MessageBox.Show("Error Update: " & ex.Message)
            Return False
      End Try
    End Functionแอดมินออกแบบเผื่อเอาไว้ หากบางคนต้องการเช็คความถูกต้องก่อน โดยจะมีการรีเทิร์น หรือคืนค่ากลับแบบ Boolean (True/False)

http://www.g2gnet.com/webboard/images/vbnet/NewPrimaryKeyFN.png
ส่วนของการเพิ่มข้อมูลเข้าไปใหม่ แอดมินจำลองการทำงานแบบง่ายๆเอาไว้ให้ดูนะครับ ...
    ' / --------------------------------------------------------------------------------
    ' / Add data and find new Primary Key values.
    Private Sub btnAdd_Click(sender As System.Object, e As System.EventArgs) Handles btnAdd.Click
      '// Input Fullname
      Dim Fullname As String
      Fullname = InputBox("Enter Fullname: ", "Sample", "")
      '//
      If Fullname = "" Then
            MessageBox.Show("You must enter a Fullname to continue.")
            Exit Sub
      ElseIf Fullname = "" Then
            Exit Sub
      End If
      '// Add new data into DataGridView.
      Dim dataTable As DataTable = DirectCast(dgvData.DataSource, DataTable)
      Dim DRow As DataRow = dataTable.NewRow()
      '// Populate new Primary Key.
      strSQL = _
            " SELECT MAX(tblContact.ContactPK) AS MaxPK FROM tblContact "
      Dim NewPK As Integer = SetupNewPK(strSQL)
      '//
      DRow("ContactPK") = NewPK
      DRow("Fullname") = Fullname
      dataTable.Rows.Add(DRow)
      dataTable.AcceptChanges()
      dataTable.Dispose()
      '// Save data into DataBase.
      strSQL = _
            " INSERT INTO tblContact(" & _
            " ContactPK, Fullname) " & _
            " VALUES(" & _
            "'" & NewPK & "', " & _
            "'" & Fullname & "'" & _
            ")"
      '// Insert or Update same as operation
      If DoSQL(strSQL) Then
            MessageBox.Show("Records Updated Completed.", "Update Status", MessageBoxButtons.OK, MessageBoxIcon.Information)
      End If
    End Subเมื่อเลือกกดปุ่ม Add PK เราก็ต้องป้อนค่า Fullname เข้าไปก่อน หากเลือก Cancel ก็ยกเลิกการทำงาน หากเลือกปุ่ม OK ก็จะนำเอาข้อมูลใหม่ไปต่อท้ายตารางกริดด้วย DataTable เพื่อแสดงผลให้เห็น จากนั้นก็ทำการ INSERT ค่า Primary Key และ Fullname เข้าไปเพื่อทำการทดสอบ
http://www.g2gnet.com/webboard/images/vbnet/NewPrimaryKeySave.png

แถมพกกับการสั่งลบข้อมูลจากรายการแถวในตารางกริด ...
    ' / --------------------------------------------------------------------------------
    ' / Delete the item you have selected.
    Private Sub btnDelete_Click(sender As System.Object, e As System.EventArgs) Handles btnDelete.Click
      If dgvData.RowCount = 0 Then Exit Sub
      '// Receive Primary Key value to confirm the deletion.
      Dim iRow As Long = dgvData.Item(0, dgvData.CurrentRow.Index).Value
      '// "" is Null protection, the solution comes from VB6.
      Dim FName As String = "" & dgvData.Item(1, dgvData.CurrentRow.Index).Value
      Dim Result As Byte = MessageBox.Show("Are you sure you want to delete the data?" & vbCrLf & _
                                             "Primary Key = " & iRow & vbCrLf & _
                                             "Fullname: " & FName, "Confirm Deletion", _
                                             MessageBoxButtons.YesNo, MessageBoxIcon.Question, MessageBoxDefaultButton.Button2)
      If Result = DialogResult.Yes Then
            '// iRow is the ContactPK or Primary key that is hidden.
            strSQL = " DELETE FROM tblContact WHERE ContactPK = " & iRow
            '// UPDATE RECORD
            DoSQL(strSQL)
            '// Refresh
            Call RetrieveData()
      End If
    End SubConclusion: หลายๆคนอาจจะมองว่าทำไมมันมีความยุ่งยากจังเลย แอดมินขอไม่อธิบายให้ฟังล่ะกันครับ เอาเป็นว่าให้ทุกๆท่านได้ลองนำไปคิด ไปลองลงมือปฏิบัติดูเอาเองกันดีกว่าครับ ... รอบหน้าเราจะมาว่ากันถึงเรื่อง IDentifier สวัสดี
ดาวน์โหลดโค้ดต้นฉบับแบบเต็ม VB.NET (2010) ได้ที่นี่

g2gsoftuser โพสต์ 2022-10-25 18:29:33

ขอบคุณครับ

MMEE007 โพสต์ 2022-12-11 21:11:45

ขอบพระคุณคัพ อาจารย์:loveliness::loveliness::loveliness:
หน้า: [1]
ดูในรูปแบบกติ: [VB.NET] พื้นฐานการสร้าง Primary Key ขึ้นมาใหม่ โดยไม่ให้ซ้ำกับค่าเดิม