【问题标题】:How do I delete specific records from a table in visual studio?如何从 Visual Studio 中的表中删除特定记录?
【发布时间】:2020-11-16 10:45:21
【问题描述】:

我现在已经多次编写和重写代码,以在文本框中输入“名称”并单击将删除与输入名称相关的行时删除记录。但是,当我运行程序并单击按钮时,会弹出消息框,说明特定记录已被删除,但是当表格显示在数据网格视图中时,记录仍然存在(它们还没有被删除)从表中删除) 请检查我的编码并告诉我其中有什么问题,我该如何解决?谢谢你 :) 另外我不得不说,我只学习了 C# 编程的基本知识。 这是我的编码:

private void btnremove_Click(object sender, EventArgs e)
{
    con.Open();
    DialogResult ans = MessageBox.Show("Are you sure you want to remove the selected records?", 
        "Confirmation For Membership Cancellation", MessageBoxButtons.YesNo, 
        MessageBoxIcon.Question);
    if (ans==DialogResult.Yes)
    {
        string sqldelete = "DELETE FROM membersdetails WHERE Name='" + txtname.Text + "'";
        string deletesql = "DELETE FROM currentstatus WHERE Name_='" + txtname.Text + "'";
        com = new SqlCommand(sqldelete,con);
        com = new SqlCommand(deletesql, con);
        SqlDataAdapter sqldataadapter = new SqlDataAdapter(com);
        com.ExecuteNonQuery();
        MessageBox.Show("Records have been removed- Membership has been  cancelled", 
           "Membership Cancellation", MessageBoxButtons.OK, MessageBoxIcon.Information);
    }
    con.Close();
    com.Dispose();
}

【问题讨论】:

  • 数据更新时不会自动重绘 DGV。您必须再次查询数据库或从 DataSet 中删除。

标签: c# database visual-studio-2013 sql-delete


【解决方案1】:

在当前状态下,您的代码存在一些问题:

  1. 下面的块,你正在覆盖你的删除机制的一部分:

        com = new SqlCommand(sqldelete,con);
        com = new SqlCommand(deletesql, con);
        SqlDataAdapter sqldataadapter = new SqlDataAdapter(com);
        com.ExecuteNonQuery();
    

    您应该能够将 sqldeletedeletesql 字符串变量合并到 1 个命令中,然后可以将其传递给 DB Engine。

  2. 从编码的角度来看,类应该遵守单一职责原则,即类担心只做一件事。在您当前的代码中,用户界面需要考虑保持用户界面更新并且保持数据库更新。为了解决这个问题,我们通常创建存储库,其任务是包装数据库操作。这还允许您测试应用程序的各个层,并在您决定进行任何更改时为您提供更大的灵活性。

  3. 目前,您的代码对 SQL 注入攻击是开放的,请考虑使用准备好的语句来解决此问题。

  4. 除此之外,我看不出您的删除代码有任何内在错误。但是,您的网格可能没有被刷新(当您认为它正在刷新时)。检查这一点的最快和最好的方法是使用 SQL Management Studio(或 Azure Data)之类的工具连接到您的数据库并直接查询表。

【讨论】:

    【解决方案2】:

    ExecuteNonQuery() 必须在最后一个新实例之后和之前执行:

        com = new SqlCommand(sqldelete,con);
        com.ExecuteNonQuery();
        com = new SqlCommand(deletesql, con);
        com.ExecuteNonQuery();
        
        // Then, you can show the table
        string sqlSelect = "SELECT * FROM yourtable WHERE bla bla...";
        SqlDataAdapter sqldataadapter = new SqlDataAdapter(sqlSelect, con);
        DataTable tbl = new DataTable();
        sqldataadapter.Fill(tbl);
        yourDataGridView.DataSource = tbl;
    

    试试这个,希望对你有帮助。

    【讨论】:

      【解决方案3】:

      以下是一个示例,可能需要进行一些更改以适应您的代码。这个想法是使用 BindingSource 设置 DataGridView 数据源,该数据源具有表中所需的列以获取成员详细信息。数据操作在一个类中,用于将前端操作与数据操作分开。请注意,不需要过度杀伤的 SqlDataAdapter。

      对于删除操作,最好使用主键,因为这是恒定的,而名称可能会在某些时候发生变化。

      以下类是读取和删除操作的模型,请确保您了解它不是复制粘贴解决方案,因此请在尝试之前花时间阅读代码。

      数据类

      using System.Collections.Generic;
      using System.Data.SqlClient;
      
      namespace YourNamespace
      {
          public class MembershipOperations
          {
              /// <summary>
              /// Connection string to your database
              /// - change TODO to your environment
              /// - Integrated Security (check this too)
              /// </summary>
              private static readonly string _connectionString =
                  "Data Source=****TODO****;" +
                  "Initial Catalog=****TODO****;" +
                  "Integrated Security=True";
      
              /// <summary>
              /// Delete a single member by primary key
              /// Recommend adding a try-catch to the open and ExecuteNonQuery lines
              /// </summary>
              /// <param name="memberIdentifier">Member primary key</param>
              /// <returns>
              /// Success of the operation
              /// </returns>
              public static bool RemoveSingleOrder(int memberIdentifier)
              {
                  bool success = false;
      
                  string deleteStatement = "DELETE FROM membersdetails  WHERE id = @id";
      
                  using (var cn = new SqlConnection { ConnectionString = _connectionString })
                  {
                      using (var cmd = new SqlCommand { Connection = cn, CommandText = deleteStatement })
                      {
      
                          cmd.Parameters.AddWithValue("id", memberIdentifier);
                          cn.Open();
                          success = cmd.ExecuteNonQuery() == 1;
                      }
                  }
      
                  return success;
      
              }
              /// <summary>
              /// Provides a list which in the frontend a user can select
              /// a member such as a ComboBox or ListBox etc.
              ///
              /// When they select a user you have code to cast the selected item
              /// to a MemberDetails instance and pass the primary key to the RemoveSingleOrder
              /// method.
              ///
              /// Note in the frontend if there are many members consider providing a incremental
              /// search feature to the frontend control displaying member details.
              /// </summary>
              /// <returns></returns>
              public static List<MemberDetails> GetMemberDetails()
              {
                  var memberDetails = new List<MemberDetails>();
      
                  /*
                   * - Create a connection and command object with
                   *   SELECT column names including 'id' primary key
                   *
                   * - Use a DataReader to loop through records into
                   *   memberDetails variable
                   */
      
                  return memberDetails;
              }
          }
          /// <summary>
          /// Place in a class file named  MemberDetails.cs
          /// </summary>
          public class MemberDetails
          {
              public int Id { get; set; }
              public string FirstName { get; set; }
              public string LastName { get; set; }
              // more properties
      
              /// <summary>
              /// Optional, can assist with debugging and/or
              /// for display purposes
              /// </summary>
              /// <returns></returns>
              public override string ToString() => $"{FirstName} {LastName}";
      
          }
      }
      

      帮助方法用默认按钮提问是否,不是是。

      使用 System.Windows.Forms;

      namespace YourNamespace
      {
          public static class Dialogs
          {
              public static bool Question(string text)
              {
                  return (MessageBox.Show(
                      text,
                      Application.ProductName,
                      MessageBoxButtons.YesNo,
                      MessageBoxIcon.Question,
                      MessageBoxDefaultButton.Button2) == DialogResult.Yes);
              }
          }
      }
      

      表单代码

      using System;
      using System.Windows.Forms;
      
      namespace YourNamespace
      {
          public partial class Form1 : Form
          {
              private readonly BindingSource _membersBindingSource = new BindingSource();
              public Form1()
              {
                  InitializeComponent();
                  Shown += Form1_Shown;
              }
              /// <summary>
              /// Setup columns in the IDE for MembersDataGridView that
              /// exclude the primary key
              /// </summary>
              /// <param name="sender"></param>
              /// <param name="e"></param>
              private void Form1_Shown(object sender, EventArgs e)
              {
                  MembersDataGridView.AutoGenerateColumns = false;
                  _membersBindingSource.DataSource = MembershipOperations.GetMemberDetails();
                  MembersDataGridView.DataSource = _membersBindingSource;
              }
      
              private void RemoveMemberButton_Click(object sender, EventArgs e)
              {
                  if (_membersBindingSource.Current == null) return;
      
                  var member = (MemberDetails)_membersBindingSource.Current;
      
                  if (!Dialogs.Question($"Remove {member}")) return;
      
                  if (!MembershipOperations.RemoveSingleOrder(member.Id))
                  {
                      MessageBox.Show($"Failed to remove {member}");
                  }
              }
          }
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-02-14
        • 2015-12-22
        • 1970-01-01
        • 1970-01-01
        • 2011-04-28
        • 2015-03-15
        相关资源
        最近更新 更多