前言:這是我在簡書的第一篇文章,目前正在學(xué)習(xí)C#,還屬于基礎(chǔ)加強(qiáng)階段,希望可以通過撰寫博客加深自己對(duì)于所學(xué)知識(shí)點(diǎn)的理解,并盡量詳細(xì)的把自己的學(xué)習(xí)過程與大家分享,希望能夠與大家一起分享交流學(xué)習(xí)心得。
當(dāng)我們從sql數(shù)據(jù)庫中讀取的數(shù)據(jù)量較多,并需要在頁面中展示出來時(shí),在一頁上全部顯示未免有點(diǎn)冗余,所以為了方便用戶查看,可以實(shí)現(xiàn)分頁瀏覽的功能,具體需求如下。
需求分析
- 從數(shù)據(jù)庫讀取數(shù)據(jù)顯示在DataGridView中;
- 實(shí)現(xiàn)分頁瀏覽,可以選擇首頁、尾頁、上一頁、下一頁,并可由用戶選擇每頁顯示的數(shù)據(jù)條數(shù)
實(shí)現(xiàn)過程分析
- 在sql數(shù)據(jù)庫中創(chuàng)建表TblTeacher
- 在vs中自定義SqlHelper類,將有關(guān)數(shù)據(jù)庫的所有操作均封裝進(jìn)去,讓用戶在編程時(shí)只專注于構(gòu)造sql語句或者存儲(chǔ)過程;
- 設(shè)計(jì)WinForm窗體,向其中添加MenuStrip和DataGridView控件;
- 編寫MenuStrip各項(xiàng)的點(diǎn)擊事件。
1.實(shí)現(xiàn)效果
WinForm窗體每頁顯示3條數(shù)據(jù)效果圖如下所示:



First表示首頁;Last表示尾頁;Prev表示前一頁;Next表示后一頁;最后一欄為combox,可由用戶選擇每頁顯示的數(shù)據(jù)條數(shù)
2.實(shí)現(xiàn)過程
創(chuàng)建表
創(chuàng)建表TblTeacher,表中包含tTId(編號(hào))、tTName(姓名)、tTGender(性別)、tTAge(年齡)、tTSalary(薪資)、tTBirthday(生日)6個(gè)字段,其中tTId為主鍵。

封裝SqlHelper類
-
應(yīng)用程序配置文件中配置連接字符串
在使用數(shù)據(jù)庫時(shí),連接字符串需多次使用到,將其寫進(jìn)配置文件中后,在程序中只需通過一句代碼就可訪問到。在App.config中configuration節(jié)點(diǎn)下添加如下代碼段:
<connectionStrings>
<add name="cl" connectionString="Data Source=(local);Initial Catalog=ItCastCn;User ID=sa;Password=123456"/>
</connectionStrings>
-
方法封裝
- GetConn() 獲取數(shù)據(jù)庫連接,返回SqlConnection類型
- ExecuteNonQuery(string sql) 執(zhí)行sql語句,返回受影響的行數(shù)int類型
- ExecuteNonQuery(string sql, CommandType type, params SqlParameter[] ps) 執(zhí)行參數(shù)化的sql語句或者存儲(chǔ)過程,返回受影響的行數(shù)int類型
- ExecuteScalar(string sql, params SqlParameter[] ps) 執(zhí)行參數(shù)化的sql語句,返回首行首列的值object類型
- GetDataTable(string sql, Dictionary<string, string> dic) 執(zhí)行參數(shù)化的sql語句,返回DataTable類型的結(jié)果集
數(shù)據(jù)庫操作流程
- 創(chuàng)建連接字符串
- 創(chuàng)建sql語句或者存儲(chǔ)過程
- 創(chuàng)建sqlcommand或者sqldataadapter對(duì)象執(zhí)行sql語句或存儲(chǔ)過程
- 獲取數(shù)據(jù)庫的返回值
- 關(guān)閉數(shù)據(jù)庫,釋放資源
namespace 分頁查詢
{
public static class SqlHelper
{
/// <summary>
/// 獲取連接
/// </summary>
/// <returns>返回?cái)?shù)據(jù)庫連接</returns>
private static SqlConnection GetConn()
{
return new SqlConnection(System.Configuration.ConfigurationManager.ConnectionStrings["cl"].ConnectionString);
}
/// <summary>
/// 獲取受影響的行數(shù),不帶參數(shù),執(zhí)行sql語句
/// </summary>
/// <returns></returns>
public static int ExecuteNonQuery(string sql)
{
return ExecuteNonQuery(sql, CommandType.Text, null);
}
/// <summary>
/// 獲取受影響的行數(shù),帶參數(shù),選擇執(zhí)行的是存儲(chǔ)過程還是普通的sql語句
/// </summary>
/// <param name="sql"></param>
/// <param name="ps"></param>
/// <returns></returns>
public static int ExecuteNonQuery(string sql, CommandType type, params SqlParameter[] ps)
{
int rows = -1;
using (SqlConnection conn = GetConn())
{
SqlCommand cmd = new SqlCommand(sql, conn);
//定義執(zhí)行語句的類型
cmd.CommandType = type;
if (ps != null)
cmd.Parameters.AddRange(ps);
conn.Open();
rows = cmd.ExecuteNonQuery();
}
return rows;
}
/// <summary>
/// 獲取首行首列的值
/// </summary>
/// <param name="sql"></param>
/// <param name="ps"></param>
/// <returns></returns>
public static object ExecuteScalar(string sql, params SqlParameter[] ps)
{
object obj = null;
using (SqlConnection conn = GetConn())
{
SqlCommand cmd = new SqlCommand(sql, conn);
if (ps != null)
cmd.Parameters.AddRange(ps);
conn.Open();
obj = cmd.ExecuteScalar();
}
return obj;
}
/// <summary>
/// 獲取一個(gè)結(jié)果集
/// </summary>
/// <param name="sql"></param>
/// <param name="ps"></param>
/// <returns></returns>
public static DataTable GetDataTable(string sql, Dictionary<string, string> dic)
{
DataTable dt = new DataTable();
using (SqlConnection conn = GetConn())
{
SqlDataAdapter adapter = new SqlDataAdapter(sql, conn);
if (dic != null)
{
SqlParameter[] ps = new SqlParameter[dic.Count];
int index = 0;
foreach (var item in dic)
{
ps[index++] = new SqlParameter(item.Key, item.Value);
}
adapter.SelectCommand.Parameters.AddRange(ps);
}
conn.Open();
adapter.Fill(dt);
}
return dt;
}
}
}
控件點(diǎn)擊事件
菜單欄子項(xiàng)點(diǎn)擊后的觸發(fā)事件,通過Text屬性判斷當(dāng)前要去第幾頁。
//填充數(shù)據(jù)到datagridview
private void fillToolStripMenuItem_Click(object sender, EventArgs e)
{
string sql = "select * from Teacher_Index";
DataTable dt = SqlHelper.GetDataTable(sql, null);
dataGridView1.DataSource = dt;
}
//當(dāng)前顯示的頁碼
int page_index;
//判斷選擇的是首頁、尾頁、前一頁、后一頁
private void Page_Click(object sender, EventArgs e)
{
//根據(jù)combox的內(nèi)容獲取一頁的行數(shù)
int page_size = Convert.ToInt32(MS_page_size.Text);
//獲取總的數(shù)據(jù)行數(shù)
int rows = GetCount();
//獲取能得到的最多的頁數(shù)
int max_rowindex = rows % page_size == 0 ? rows / page_size : rows / page_size + 1;
ToolStripMenuItem page = sender as ToolStripMenuItem;
switch (page.Text)
{
//首頁
case "First":
page_index = 1;
break;
//尾頁
case "Last":
page_index = max_rowindex;
break;
//前一頁
case "Prev":
if (page_index <= 1)
//已經(jīng)是首頁
page_index = 1;
else
page_index--;
break;
//下一頁
case "Next":
if (page_index >= max_rowindex)
//已經(jīng)是尾頁
page_index = max_rowindex;
else
page_index++;
break;
}
//指定dataGridView1的數(shù)據(jù)源
dataGridView1.DataSource = GetData();
}
//獲取指定行的數(shù)據(jù)
private DataTable GetData()
{
int page_size = Convert.ToInt32(MS_page_size.Text);
//獲取指定列數(shù)的內(nèi)容
string sql = "select * from Teacher_Index where row_index between @startindex and @endindex";
//給參數(shù)賦值
Dictionary<string, string> dic = new Dictionary<string, string>();
dic.Add("@startindex", (page_size * (page_index - 1)+1).ToString());
dic.Add("@endindex", (page_size * page_index).ToString());
return SqlHelper.GetDataTable(sql, dic);
}
private void Form1_Load(object sender, EventArgs e)
{
//初始化顯示第一頁
page_index = 1;
//默認(rèn)每頁顯示3行數(shù)據(jù)。因本次試驗(yàn)數(shù)據(jù)較少,所以選擇每頁顯示3、4、5條數(shù)據(jù)
MS_page_size.SelectedIndex = 0;
}
//獲取數(shù)據(jù)行數(shù)
private int GetCount()
{
int rows = 0;
//獲取表的行數(shù)
string sql = "select COUNT(*) from Teacher_Index";
rows = Convert.ToInt32(SqlHelper.ExecuteScalar(sql, null));
return rows;
}
3.總結(jié)
至此,已可實(shí)現(xiàn)從數(shù)據(jù)庫中讀取數(shù)據(jù)并將其分頁瀏覽,可由用戶自定義選擇每頁顯示的數(shù)據(jù)條數(shù),方便查詢。