C # получение результатов из базы данных SQL Server для отображения в поле со списком через класс

#c# #sql-server

#c# #sql-server

Вопрос:

Я очень новичок в C #, поэтому, пожалуйста, простите мое невежество. У меня есть таблица SQL Server, и я пытаюсь получить результаты запроса select select из этой таблицы в поле со списком form в C #.

Что я пытаюсь сделать, так это создать класс, который будет выполнять хранимую процедуру на стороне базы данных, и мой камень преткновения — как интегрировать этот класс в код, чтобы результаты отображались в раскрывающемся списке в C #.

Вот что у меня есть на данный момент в C #. Ваша помощь очень ценится.

 using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Data;
using System.Data.SqlClient;
using System.Configuration;

namespace MedicalOffice
{
    public class DBAIdSelect
    {
        public void SelectPractice()
        {
            using (SqlConnection cn = new SqlConnection())
            {
                cn.ConnectionString = GetConnectionString();
                cn.Open(); 

                using (SqlCommand cmd = new SqlCommand("SelectPracticeID"))
                {
                    cmd.Connection = cn;
                    cmd.CommandType = CommandType.StoredProcedure;
                    cmd.ExecuteNonQuery();
                }
            }
        }

        private string GetConnectionString()
        {
            string conString = ConfigurationManager.ConnectionStrings["MyConnString"].ConnectionString;
            return conString;
        }
    }
 }
  

Таблица SQL Server:

 SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
SET ANSI_PADDING ON
GO

CREATE TABLE [dbo].[Practices]
(
    [PracticeID] [int] IDENTITY(1,1) NOT NULL,
    [PracticeName] [varchar](50) NULL,
    [Address1] [varchar](50) NULL,
    [Address2] [varchar](50) NULL,
    [City] [varchar](50) NULL,
    [State] [char](2) NULL,
    [Zip] [varchar](10) NULL,
    [IsActive] [bit] NULL,
    [DateCreated] [date] NULL 
        CONSTRAINT [DF_Practices_DateCreated]  DEFAULT (getdate()),
    [CreatedBy] [int] NULL,
    [DateModified] [date] NULL,
    [DateModifiedBy] [int] NULL,

    CONSTRAINT [PK_Practices] 
        PRIMARY KEY CLUSTERED ([PracticeID] ASC)
                WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF,
                      IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, 
                      ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
GO

SET ANSI_PADDING OFF
GO
  

и хранимая процедура:

 create proc [dbo].[SelectPracticeID]
as
    select PracticeID
    from dbo.Practices
GO
  

Комментарии:

1. вы не задали вопрос? Но вашим следующим шагом будет возврат значений из вашего класса. cmd.ExecuteNonQuery(); не сработает — вам нужно вернуть возвращенные значения.

2. Веб-формы, winforms, MVC, WCF? Какую технологию вы используете?

3. Вы вызываете хранимый для извлечения записей, но вы ничего не делаете с возвратом. Например, если вы получаете datareader, вы должны читать записи оттуда. Также соединение не закрывается. В строке есть много примеров кода о том, как сделать то, чего вы пытаетесь достичь.

4. На данный момент я использую простую и понятную форму из Visual Studio. Мой камень преткновения заключается в том, как вернуть данные обратно в форму.

Ответ №1:

Вы можете использовать этот класс всякий раз, когда хотите вызвать хранимую процедуру, и она возвращает DataTable :

 class myclass
{
     public DataTable SelectData(string proc, SqlParameter[] param)
     {
            DataTable Table = new DataTable();
            SqlCommand Cmd = new SqlCommand();
            Cmd.CommandType = CommandType.StoredProcedure;
            Cmd.CommandText = proc;
            Cmd.Connection = Acces.Connection;

            if (param != null)
                for (int i = 0; i < param.Length; i  )
                {
                    Cmd.Parameters.Add(param[i]);
                }

            SqlDataAdapter Adapter = new SqlDataAdapter(Cmd);
            Adapter.Fill(Table);

            return Table;
        }
     }
  

Поэтому всякий раз, когда вы хотите использовать какую-либо хранимую процедуру, которая возвращает набор результатов, используйте ее, и если вы хотите выполнить какие-либо данные :

 public void ExecuteData(string proc, SqlParameter[] param)
{
    SqlCommand Cmd = new SqlCommand();
    Cmd.CommandType = CommandType.StoredProcedure;
    Cmd.CommandText = proc;
    Cmd.Connection = Acces.Connection;

    if (param != null)
    {
        Cmd.Parameters.AddRange(param);
    }

    Cmd.ExecuteNonQuery();
}
  

Создайте эти две функции в своем классе и всякий раз, когда вы хотите вызвать класс, чтобы вернуть вам некоторые данные или выполнить некоторые данные, такие как Insert, Update, Delete …

Вам просто нужно вызвать

 function("Stored_Proc_Name", Parameters);
  

Пример :

Я хочу получить процедуру выбора, подобную вашей:

   myclass classs = new myclass();
  DataTable Table = new DataTable();
  Table  = classs.SelectData("SelectPracticeID",null); //=cause there is no paramters in your stored proc 
  

Таким Table образом, будет храниться полная информация, отправленная вашей базой данных

Комментарии:

1. Лично я не поклонник нетипизированного (он же «свободный») Таблицы данных и наборы данных .. начиная с 2005 года.

Ответ №2:

Я бы предложил создать DTO / Simple Poco для ваших данных.

Этот «способ» требует немного больше усилий….НО ваша объектная модель будет чистой, приятной и поддерживаемой.

Таблицы данных были хороши в 2003 году. Это больше не 2003. Приведенное ниже — «ORM для бедных», но его легко перенести в Entity-Framework или NHibernate в будущем. Таблицы данных, наборы данных, особенно нетипизированные, нелегко перенести.

 [Serializable]
public partial class Practice
{
    public int PracticeKey { get; set; }                   
    public string PracticeName { get; set; }                   
}

[Serializable]
public class PracticeCollection : ICollection<Practice>
{
}   

internal static class PracticeDefaultLayout
{
    public static readonly int PRACTICE_KEY = 0;
    public static readonly int PRACTICENAME = 1;

}


public class PracticeSerializer
{   

    public PracticeCollection SerializeCollection(IDataReader dataReader)
    {
        Practice item = new Practice();
        PracticeCollection returnCollection = new PracticeCollection();
        try
        {

            int fc = dataReader.FieldCount;//just an FYI value

            int counter = 0;//just an fyi of the number of rows

            while (dataReader.Read())
            {

                if (!(dataReader.IsDBNull(PracticeSearchResultsLayouts.PRACTICE_KEY)))
                {
                    item = new Practice() { PracticeKey = dataReader.GetInt32(PracticeSearchResultsLayouts.PRACTICE_KEY) };

                    if (!(dataReader.IsDBNull(PracticeSearchResultsLayouts.PRACTICENAME)))
                    {
                        item.PracticeName = dataReader.GetString(PracticeSearchResultsLayouts.PRACTICENAME);
                    }


                    returnCollection.Add(item);
                }

                counter  ;
            }

            return returnCollection;

        }
        //no catch here... see  http://blogs.msdn.com/brada/archive/2004/12/03/274718.aspx
        finally
        {
            if (!((dataReader == null)))
            {
                try
                {
                    dataReader.Close(); /* very important */ /* note, if your datareader had MULTIPLE resultsets, you would not close it here */
                }
                catch
                {
                }
            }
        }
    }
}








namespace MedicalOffice
{
    public class PracticeDataLayer
    {
        public ICollection<Practice> GetAllPractices()
        {
            using (SqlConnection cn = new SqlConnection())
            {
                cn.ConnectionString = GetConnectionString();
                cn.Open(); 

                using (SqlCommand cmd = new SqlCommand("SelectPracticeID"))
                {
                    cmd.Connection = cn;
                    cmd.CommandType = CommandType.StoredProcedure;
                    IDataReader idr = cmd.ExecuteReader();
                    return new PracticeSerializer().SerializeCollection(idr);
                    ////  idr.Close(); /* very important, currently the serializer closes it..so commented out here */  /* note, if your datareader had MULTIPLE resultsets, you would close the datareader AFTER you used all the resultsets */
                }
            }
        }

        private string GetConnectionString()
        {
            string conString = ConfigurationManager.ConnectionStrings["MyConnString"].ConnectionString;
            return conString;
        }
    }
 }