精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

C#邂逅SQLite:開啟輕量級數據之旅

開發 前端
在 C# 的開發世界里,SQLite 數據庫以其輕量級、易上手等特性,為我們提供了一種高效的數據存儲和管理方案。從搭建開發環境、引入 SQLite 支持,到創建數據庫連接,再到進行各種基本的數據操作,如創建表、插入、查詢、更新和刪除數據,每一步都是構建強大數據驅動應用的基石。

1. 數據庫界的 “輕騎兵” SQLite

在數據庫的廣袤天地里,SQLite 就像是一位低調卻實力非凡的 “輕騎兵”。它以輕量級、零配置、跨平臺等諸多特性,在眾多數據庫中獨樹一幟。

SQLite 到底有多輕量級呢?它的整個數據庫引擎可以被編譯成一個極小的庫文件,在運行時占用極少的系統資源,甚至在一些資源受限的嵌入式設備中,也能輕松 “安營扎寨” 。與那些需要復雜安裝和配置的數據庫不同,SQLite 堪稱 “零配置” 的典范,你幾乎不需要進行任何繁瑣的設置,就能快速上手使用。而且,無論是 Windows、Linux 還是 Mac OS 等主流操作系統,又或是 Android、iOS 等移動平臺,SQLite 都能完美適配,真正做到了 “一處編寫,隨處運行”。

也正是因為這些特性,SQLite 在眾多場景中都大顯身手。在移動應用開發中,很多手機 APP 都用 SQLite 來存儲用戶的個性化設置、本地緩存數據等,如常見的筆記類應用,用戶記錄的筆記內容就可以安全地保存在 SQLite 數據庫中;在桌面應用領域,一些小型的工具軟件,像簡單的記賬軟件、個人日程管理軟件等,SQLite 也能為其提供高效的數據存儲服務;而在嵌入式系統中,從智能手表到智能家居設備,SQLite 憑借其小巧靈活的特點,成為了數據存儲的理想選擇。

看到這里,如果你正好在進行 C# 項目開發,是不是已經迫不及待想知道如何在 C# 中巧妙運用 SQLite 了呢?別著急,接下來就為大家詳細介紹在 C# 中搭建 SQLite 數據庫的具體步驟。

2. 搭建 C# 與 SQLite 的橋梁

2.1 準備開發環境

首先,你需要安裝一款強大的開發工具 ——Visual Studio。它就像是一個超級 “魔法工具箱”,為 C# 開發者提供了豐富的功能和便捷的開發體驗。你可以從微軟官方網站下載并安裝最新版本的 Visual Studio,安裝過程中,根據自己的需求勾選相關組件,比如 “.NET 桌面開發” 等,這些組件將為我們后續的開發工作打下堅實的基礎。

此外,還需要確保你的開發環境中已安裝了.NET Framework 或.NET Core。.NET Framework 是微軟開發的一個非常重要的軟件框架,它為 C# 程序提供了運行時的支持和各種基礎類庫;而.NET Core 則是新一代的跨平臺、高性能的開源開發框架,具有更靈活的部署和運行方式。如果你的系統中尚未安裝,別擔心,同樣可以從微軟官方網站獲取并安裝適合你系統的版本。

2.2 引入 SQLite 支持

在 Visual Studio 中,我們可以借助強大的 NuGet 包管理器來引入 SQLite 的支持。NuGet 就像是一個軟件包的 “大超市”,里面應有盡有。打開你的項目,在 “解決方案資源管理器” 中右鍵點擊項目名稱,選擇 “管理 NuGet 程序包”。在彈出的窗口中,切換到 “瀏覽” 選項卡,然后在搜索框中輸入 “SQLite” 。這時,你會看到兩個常見的包:System.Data.SQLite 和 Microsoft.Data.Sqlite。

System.Data.SQLite 提供了豐富的功能和工具,比如 SQLite 的命令行界面和數據庫設計工具,能滿足較為復雜的開發需求;而 Microsoft.Data.Sqlite 則是由微軟官方提供的,它與.NET Core 的集成度更高,在.NET Core 項目中使用起來更加方便和穩定。你可以根據自己的項目類型和需求選擇其中一個進行安裝,點擊 “安裝” 按鈕,NuGet 會自動下載并添加相關的依賴項到你的項目中,是不是很簡單呢?

2.3 創建數據庫連接

安裝好相關包后,接下來就可以創建數據庫連接了。在 C# 中,我們使用 SQLiteConnection 類來創建連接對象。來看一段簡單的代碼示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";// 數據庫文件路徑using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();// 這里可以執行各種數據庫操作}}}

在這段代碼中,首先定義了數據庫文件的路徑dbPath,這里我們將其命名為 “example.db” 。然后,使用SQLiteConnection創建了一個連接對象conn,并在構造函數中傳入了連接字符串。連接字符串就像是一把 “鑰匙”,它包含了連接數據庫所需的各種信息,其中Data Source指定了數據庫文件的路徑,Versinotallow=3表示使用 SQLite 的版本 3,這是目前廣泛使用的版本。通過conn.Open()方法,我們打開了與數據庫的連接,此時,就像打開了一扇通往數據世界的大門,后續可以在這個連接的基礎上執行各種數據庫操作了。

需要注意的是,連接字符串中的數據庫路徑要根據實際情況進行設置,如果是相對路徑,要確保其相對于項目的正確位置;如果是絕對路徑,要保證路徑的準確性和完整性。同時,在使用完數據庫連接后,一定要及時關閉連接,釋放資源,這也是良好的編程習慣。通過以上步驟,我們就成功地在 C# 中搭建起了與 SQLite 數據庫的連接,為后續的數據操作做好了準備。

3. SQLite 數據庫基本操作

在成功搭建好 C# 與 SQLite 的連接后,接下來就可以對 SQLite 數據庫進行各種基本操作了,這些操作就像是搭建數據大廈的基石,是我們開發過程中必不可少的環節。

3.1 創建數據庫和表

在 SQLite 中,創建數據庫實際上就是創建一個數據庫文件,而創建表則是在這個文件中定義數據的存儲結構。在 C# 中,我們可以使用SQLiteCommand對象來執行 SQL 語句,從而完成這些操作。來看下面的代碼示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){// 創建表cmd.CommandText = @"CREATE TABLE IF NOT EXISTS Users (Id INTEGER PRIMARY KEY AUTOINCREMENT,Name TEXT NOT NULL,Email TEXT NOT NULL UNIQUE)";cmd.ExecuteNonQuery();Console.WriteLine("表創建成功!");}}}}

在這段代碼中,首先通過SQLiteConnection打開了與數據庫的連接。然后,創建了一個SQLiteCommand對象cmd,并設置其CommandText屬性為創建表的 SQL 語句。在這個CREATE TABLE語句中,IF NOT EXISTS表示如果表不存在才創建,這可以避免重復創建表時引發的錯誤。Users是表的名稱,Id字段被定義為INTEGER類型,并且設置為PRIMARY KEY AUTOINCREMENT,這意味著它是主鍵,并且會自動遞增,確保每一行數據都有一個唯一的標識;Name字段是TEXT類型,且NOT NULL,表示不能為空,用于存儲用戶的姓名;Email字段同樣是TEXT類型,NOT NULL UNIQUE表示不能為空且值必須唯一,用于存儲用戶的郵箱地址。最后,通過cmd.ExecuteNonQuery()方法執行這個 SQL 語句,創建表。如果執行成功,會在控制臺輸出 “表創建成功!” 的提示信息。

3.2 插入數據

數據插入是向數據庫中添加新記錄的操作。為了確保數據插入的安全性和可靠性,我們通常使用參數化查詢。下面是一個插入數據的代碼示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){// 插入數據cmd.CommandText = "INSERT INTO Users (Name, Email) VALUES (@name, @email)";cmd.Parameters.AddWithValue("@name", "張三");cmd.Parameters.AddWithValue("@email", "zhangsan@example.com");int rowsAffected = cmd.ExecuteNonQuery();Console.WriteLine($"{rowsAffected} 行受影響,數據插入成功!");}}}}

在這段代碼中,首先定義了插入數據的 SQL 語句,其中@name和@email是參數占位符。然后,通過cmd.Parameters.AddWithValue方法為這些參數賦值,這樣可以避免 SQL 注入攻擊。假設沒有使用參數化查詢,而是直接將用戶輸入的數據拼接在 SQL 語句中,如果用戶輸入的數據包含惡意的 SQL 代碼,比如'; DROP TABLE Users; --,就可能導致整個Users表被刪除,造成嚴重的數據丟失。而參數化查詢采用了預編譯的方法,先將 SQL 語句中可被客戶端控制的參數集進行編譯,生成對應的臨時變量集,再使用對應的設置方法,為臨時變量集里面的元素進行賦值,并且在賦值時會對傳入的參數進行強制類型檢查和安全檢查 ,從而有效避免了 SQL 注入的風險。最后,通過cmd.ExecuteNonQuery()方法執行插入操作,該方法會返回受影響的行數,通過判斷這個返回值,我們可以知道數據是否成功插入。如果返回值大于 0,說明插入成功,并在控制臺輸出相應的提示信息。

3.3 查詢數據

查詢數據是從數據庫中獲取所需信息的重要操作。在 C# 中,我們使用SELECT語句來執行查詢,并通過SQLiteDataReader來讀取查詢結果。以下是查詢數據的代碼示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){// 查詢數據cmd.CommandText = "SELECT * FROM Users";using (SQLiteDataReader reader = cmd.ExecuteReader()){while (reader.Read()){int id = reader.GetInt32(0);string name = reader.GetString(1);string email = reader.GetString(2);Console.WriteLine($"ID: {id}, Name: {name}, Email: {email}");}}}}}}

在這段代碼中,首先設置SQLiteCommand的CommandText為SELECT * FROM Users,表示查詢Users表中的所有數據。然后,通過cmd.ExecuteReader()方法執行查詢,并返回一個SQLiteDataReader對象reader,它就像是一個數據讀取器,用于逐行讀取查詢結果。在while循環中,reader.Read()方法用于移動到下一行數據,如果還有下一行數據,該方法返回true,否則返回false。在循環內部,通過reader.GetInt32(0)獲取第一列(即Id列)的數據,并轉換為int類型;通過reader.GetString(1)獲取第二列(即Name列)的數據,并轉換為string類型;通過reader.GetString(2)獲取第三列(即Email列)的數據,并轉換為string類型。最后,將這些數據輸出到控制臺,展示查詢結果。

3.4 更新和刪除數據

更新和刪除數據是對數據庫中已有數據進行修改和移除的操作,這兩個操作都需要謹慎使用,因為一旦操作失誤,可能會導致數據的錯誤修改或丟失。下面分別來看更新和刪除數據的代碼示例。

更新數據的代碼示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){// 更新數據cmd.CommandText = "UPDATE Users SET Email = @newEmail WHERE Name = @name";cmd.Parameters.AddWithValue("@newEmail", "new_zhangsan@example.com");cmd.Parameters.AddWithValue("@name", "張三");int rowsAffected = cmd.ExecuteNonQuery();Console.WriteLine($"{rowsAffected} 行受影響,數據更新成功!");}}}}

在這段更新數據的代碼中,SQLiteCommand的CommandText設置為UPDATE Users SET Email = @newEmail WHERE Name = @name,表示要更新Users表中Name為 “張三” 的記錄的Email字段為new_zhangsan@example.com。同樣使用了參數化查詢來確保安全,通過cmd.Parameters.AddWithValue方法為參數賦值。然后,通過cmd.ExecuteNonQuery()方法執行更新操作,并根據返回的受影響行數來判斷更新是否成功。

刪除數據的代碼示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){// 刪除數據cmd.CommandText = "DELETE FROM Users WHERE Name = @name";cmd.Parameters.AddWithValue("@name", "張三");int rowsAffected = cmd.ExecuteNonQuery();Console.WriteLine($"{rowsAffected} 行受影響,數據刪除成功!");}}}}

在這段刪除數據的代碼中,SQLiteCommand的CommandText設置為DELETE FROM Users WHERE Name = @name,表示要刪除Users表中Name為 “張三” 的記錄。還是通過參數化查詢為參數賦值,再通過cmd.ExecuteNonQuery()方法執行刪除操作,并根據返回的受影響行數來判斷刪除是否成功。需要特別注意的是,在執行更新和刪除操作時,一定要確保WHERE條件設置準確,否則可能會誤操作大量數據,造成不可挽回的損失。

4. SQLite 使用進階技巧

4.1 使用事務處理

在數據庫操作中,事務處理就像是一場精心策劃的團隊行動,所有操作要么齊心協力全部成功,要么就一起回到最初的狀態,絕不允許出現部分成功的 “半吊子” 情況。這對于確保數據的一致性和完整性至關重要。

在 SQLite 中,我們可以使用SQLiteTransaction類來進行事務處理。來看一個簡單的代碼示例,假設我們要在一個銀行賬戶表中進行資金轉賬操作,從賬戶 A 向賬戶 B 轉賬 100 元:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "bank.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteTransaction transaction = conn.BeginTransaction()){try{using (SQLiteCommand cmd = conn.CreateCommand()){// 從賬戶A減去100元cmd.CommandText = "UPDATE Accounts SET Balance = Balance - 100 WHERE AccountID = @accountA";cmd.Parameters.AddWithValue("@accountA", "A123");cmd.ExecuteNonQuery();// 向賬戶B增加100元cmd.CommandText = "UPDATE Accounts SET Balance = Balance + 100 WHERE AccountID = @accountB";cmd.Parameters.AddWithValue("@accountB", "B456");cmd.ExecuteNonQuery();}// 所有操作成功,提交事務transaction.Commit();Console.WriteLine("轉賬成功!");}catch (Exception ex){// 出現異常,回滾事務transaction.Rollback();Console.WriteLine("轉賬失敗:" + ex.Message);}}}}}

在這段代碼中,首先通過conn.BeginTransaction()方法開始一個事務,并返回一個SQLiteTransaction對象transaction。然后,在try塊中執行兩個UPDATE操作,分別從賬戶 A 減去 100 元,向賬戶 B 增加 100 元。如果這兩個操作都成功執行,就調用transaction.Commit()方法提交事務,將這些更改永久保存到數據庫中。但如果在執行過程中出現任何異常,比如網絡中斷、數據庫連接錯誤等,就會進入catch塊,調用transaction.Rollback()方法回滾事務,撤銷之前執行的所有操作,使數據庫恢復到事務開始前的狀態,從而保證了數據的一致性和完整性。

4.2 參數化查詢

參數化查詢是數據庫操作中的一項重要安全技術,它就像是一道堅固的防線,能夠有效預防 SQL 注入攻擊。

SQL 注入攻擊是一種常見的網絡攻擊方式,攻擊者通過在輸入參數中注入惡意的 SQL 語句,改變原 SQL 語句的邏輯,從而獲取或篡改數據庫中的數據。比如,在一個用戶登錄系統中,如果沒有使用參數化查詢,代碼可能是這樣的:

string username = "admin'; DROP TABLE Users; --";string password = "any";string sql = $"SELECT * FROM Users WHERE UserName = '{username}' AND Password = '{password}'";

在這個例子中,如果用戶輸入的username是admin'; DROP TABLE Users; --,那么最終執行的 SQL 語句就會變成:

SELECT * FROM Users WHERE UserName = 'admin'; DROP TABLE Users; --' AND Password = 'any'

其中,--是 SQL 中的注釋符號,會導致后面的密碼驗證條件被忽略,并且DROP TABLE Users語句會被執行,從而刪除整個Users表,造成嚴重的數據丟失。

而使用參數化查詢,代碼就會變得安全可靠:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";string username = "admin'; DROP TABLE Users; --";string password = "any";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){cmd.CommandText = "SELECT * FROM Users WHERE UserName = @username AND Password = @password";cmd.Parameters.AddWithValue("@username", username);cmd.Parameters.AddWithValue("@password", password);using (SQLiteDataReader reader = cmd.ExecuteReader()){if (reader.HasRows){Console.WriteLine("登錄成功");}else{Console.WriteLine("登錄失敗");}}}}}}

在這段代碼中,@username和@password是參數占位符,實際的參數值通過cmd.Parameters.AddWithValue方法傳入。這樣,數據庫會將參數值作為普通數據處理,而不是 SQL 語句的一部分,從而有效防止了 SQL 注入攻擊。即使用戶輸入了惡意的 SQL 代碼,也不會對數據庫造成任何威脅。

4.3 性能優化

在數據庫應用中,性能優化是一個永恒的話題,它直接關系到應用的響應速度和用戶體驗。對于 SQLite 數據庫,我們可以通過創建索引和合理使用緩存等方法來提升性能。

索引是提高查詢效率的重要手段,它就像是一本書的目錄,能夠幫助我們快速定位到所需的數據。在 SQLite 中,我們可以使用CREATE INDEX語句來創建索引。例如,在Users表的Email字段上創建索引:

CREATE INDEX idx_users_email ON Users (Email);

創建索引后,當我們執行查詢語句SELECT * FROM Users WHERE Email = 'test@example.com'時,數據庫可以利用索引快速定位到符合條件的記錄,而不需要全表掃描,從而大大提高了查詢效率。

除了索引,合理使用緩存也能顯著提升性能。SQLite 本身具有頁緩存機制,它會緩存數據庫文件中的頁面。當查詢需要訪問某個頁面時,SQLite 會首先查找頁緩存中是否已經緩存了該頁面。如果已經緩存,則直接使用緩存中的頁面;如果沒有緩存,則從磁盤上讀取頁面,并將其緩存到頁緩存中。這樣可以減少磁盤 I/O 次數,提高查詢效率。在實際應用中,我們還可以根據具體需求,在應用層實現更高級的緩存策略,比如緩存查詢結果等,進一步減少數據庫的負載。

4.4 錯誤處理

在進行數據庫操作時,錯誤處理是必不可少的環節。數據庫操作可能會因為各種原因失敗,如連接錯誤、SQL 語法錯誤、數據約束沖突等。如果不進行有效的錯誤處理,可能會導致應用程序崩潰或出現不可預測的行為。

在 C# 中,我們可以使用try-catch塊來捕獲和處理數據庫操作中的異常。以下是一個示例:

using System.Data.SQLite;class Program{static void Main(){string dbPath = "example.db";using (SQLiteConnection conn = new SQLiteConnection($"Data Source={dbPath};Versinotallow=3;")){try{conn.Open();using (SQLiteCommand cmd = conn.CreateCommand()){cmd.CommandText = "INSERT INTO Users (Name, Email) VALUES ('InvalidEmail', 'invalid-email')";cmd.ExecuteNonQuery();}}catch (SQLiteException ex){Console.WriteLine("數據庫操作錯誤:" + ex.Message);// 根據不同的錯誤碼進行更詳細的處理switch (ex.ErrorCode){case 1: // 示例錯誤碼,實際根據SQLite錯誤碼文檔Console.WriteLine("可能是SQL語法錯誤");break;case 19: // 示例錯誤碼,如數據約束沖突Console.WriteLine("數據違反約束,可能是唯一鍵沖突等");break;default:Console.WriteLine("其他數據庫錯誤");break;}}}}}

在這段代碼中,try塊中執行插入數據的操作。如果在執行過程中出現SQLiteException異常,就會進入catch塊。在catch塊中,首先輸出錯誤信息,然后通過switch語句根據不同的錯誤碼進行更詳細的處理。這樣可以讓我們及時發現和解決數據庫操作中的問題,保證應用程序的穩定性和可靠性。

5. 實戰案例:C# 程序中的 SQLite 應用

理論知識和技巧儲備得差不多啦,接下來就通過一個實戰案例,讓大家更直觀地感受 C# 與 SQLite 的 “默契配合”。我們來開發一個簡單的學生管理系統,看看如何在 C# 程序中巧妙地集成 SQLite 數據庫,實現數據的增刪改查功能。

5.1 項目結構搭建

首先,在 Visual Studio 中創建一個新的 C# 控制臺應用程序項目,命名為 “StudentManagementSystem”。然后,按照之前介紹的方法,通過 NuGet 包管理器引入Microsoft.Data.Sqlite包,為項目添加 SQLite 的支持。

5.2 數據庫設計

在這個學生管理系統中,我們設計一個名為 “Students” 的表,用于存儲學生的相關信息。表結構如下:

字段名

數據類型

說明

Id

integer

學生 ID,主鍵,自增長

Name

text

學生姓名

Age

integer

學生年齡

Grade

text

學生年級

5.3 代碼實現

5.3.1 創建數據庫連接和表

在Program.cs文件中,編寫以下代碼來創建數據庫連接和 “Students” 表:

using System;using Microsoft.Data.Sqlite;class Program{static string connectionString = "Data Source=students.db;Versinotallow=3;";static void Main(){using (SqliteConnection conn = new SqliteConnection(connectionString)){conn.Open();CreateTable(conn);// 后續的增刪改查操作可以在這里調用}}static void CreateTable(SqliteConnection conn){string createTableSql = @"CREATE TABLE IF NOT EXISTS Students (Id INTEGER PRIMARY KEY AUTOINCREMENT,Name TEXT NOT NULL,Age INTEGER NOT NULL,Grade TEXT NOT NULL)";using (SqliteCommand cmd = new SqliteCommand(createTableSql, conn)){cmd.ExecuteNonQuery();Console.WriteLine("Students表創建成功!");}}}

在這段代碼中,首先定義了一個連接字符串connectionString,指定了數據庫文件名為 “students.db” 。在Main方法中,創建了一個SqliteConnection對象并打開連接。然后調用CreateTable方法,在該方法中,使用CREATE TABLE語句創建 “Students” 表,如果表已經存在則不會重復創建。通過SqliteCommand對象執行這個 SQL 語句,當表創建成功后,會在控制臺輸出提示信息。

5.3.2 插入數據

在Program.cs中添加插入數據的方法:

static void InsertStudent(SqliteConnection conn, string name, int age, string grade){string insertSql = "INSERT INTO Students (Name, Age, Grade) VALUES (@name, @age, @grade)";using (SqliteCommand cmd = new SqliteCommand(insertSql, conn)){cmd.Parameters.AddWithValue("@name", name);cmd.Parameters.AddWithValue("@age", age);cmd.Parameters.AddWithValue("@grade", grade);int rowsAffected = cmd.ExecuteNonQuery();if (rowsAffected > 0){Console.WriteLine("學生數據插入成功!");}}}

這個方法接收一個已打開的數據庫連接conn,以及學生的姓名、年齡和年級信息。通過INSERT INTO語句將學生數據插入到 “Students” 表中,同樣使用參數化查詢來確保數據插入的安全性。如果插入操作成功,受影響的行數會大于 0,此時會在控制臺輸出成功提示信息。

5.3.3 查詢數據

接著添加查詢數據的方法,用于獲取所有學生的信息并輸出:

static void QueryStudents(SqliteConnection conn){string querySql = "SELECT * FROM Students";using (SqliteCommand cmd = new SqliteCommand(querySql, conn)){using (SqliteDataReader reader = cmd.ExecuteReader()){while (reader.Read()){int id = reader.GetInt32(0);string name = reader.GetString(1);int age = reader.GetInt32(2);string grade = reader.GetString(3);Console.WriteLine($"ID: {id}, Name: {name}, Age: {age}, Grade: {grade}");}}}}

在這個方法中,使用SELECT * FROM Students語句查詢 “Students” 表中的所有數據。通過SqliteCommand執行查詢,并使用SqliteDataReader逐行讀取查詢結果。在讀取過程中,根據字段的索引獲取相應的數據,并將其輸出到控制臺,展示每個學生的詳細信息。

5.3.4 更新數據

再添加更新數據的方法,用于修改指定學生的信息:

static void UpdateStudent(SqliteConnection conn, int id, string newName, int newAge, string newGrade){string updateSql = "UPDATE Students SET Name = @newName, Age = @newAge, Grade = @newGrade WHERE Id = @id";using (SqliteCommand cmd = new SqliteCommand(updateSql, conn)){cmd.Parameters.AddWithValue("@newName", newName);cmd.Parameters.AddWithValue("@newAge", newAge);cmd.Parameters.AddWithValue("@newGrade", newGrade);cmd.Parameters.AddWithValue("@id", id);int rowsAffected = cmd.ExecuteNonQuery();if (rowsAffected > 0){Console.WriteLine("學生數據更新成功!");}}}

該方法接收一個已打開的數據庫連接conn,以及要更新的學生 ID 和新的學生信息。通過UPDATE語句更新 “Students” 表中指定Id的學生記錄,將其姓名、年齡和年級更新為新的值。同樣使用參數化查詢,并根據受影響的行數判斷更新操作是否成功,若成功則輸出提示信息。

5.3.5 刪除數據

最后添加刪除數據的方法,用于刪除指定學生的記錄:

static void DeleteStudent(SqliteConnection conn, int id){string deleteSql = "DELETE FROM Students WHERE Id = @id";using (SqliteCommand cmd = new SqliteCommand(deleteSql, conn)){cmd.Parameters.AddWithValue("@id", id);int rowsAffected = cmd.ExecuteNonQuery();if (rowsAffected > 0){Console.WriteLine("學生數據刪除成功!");}}}

這個方法接收一個已打開的數據庫連接conn和要刪除的學生 ID。通過DELETE FROM語句刪除 “Students” 表中指定Id的學生記錄,使用參數化查詢確保安全,并根據受影響的行數判斷刪除操作是否成功,成功則輸出提示信息。

5.4 測試代碼

在Main方法中調用上述方法,對學生管理系統的各項功能進行測試:

static void Main(){using (SqliteConnection conn = new SqliteConnection(connectionString)){conn.Open();CreateTable(conn);// 插入數據InsertStudent(conn, "張三", 18, "高三");InsertStudent(conn, "李四", 17, "高二");// 查詢數據Console.WriteLine("查詢所有學生信息:");QueryStudents(conn);// 更新數據UpdateStudent(conn, 1, "張大三", 19, "大一");// 再次查詢數據,查看更新結果Console.WriteLine("更新后查詢所有學生信息:");QueryStudents(conn);// 刪除數據DeleteStudent(conn, 2);// 再次查詢數據,查看刪除結果Console.WriteLine("刪除后查詢所有學生信息:");QueryStudents(conn);}}

在Main方法中,首先創建數據庫連接并打開,然后創建 “Students” 表。接著插入兩條學生數據,查詢所有學生信息,展示插入后的結果。之后更新 ID 為 1 的學生信息,再次查詢以查看更新后的結果。最后刪除 ID 為 2 的學生數據,再次查詢以驗證數據是否被成功刪除。每一步操作都伴隨著相應的提示信息,方便我們了解系統的運行狀態。通過這個簡單的學生管理系統實戰案例,相信大家已經對 C# 中 SQLite 數據庫的使用有了更深入的理解和掌握。

6. 常見問題與解決方法

在 C# 中使用 SQLite 時,難免會遇到一些 “小麻煩”,下面就為大家盤點一些常見問題,并提供相應的解決方法。

6.1 數據庫連接失敗

這是最常見的問題之一,可能的原因有很多。比如,連接字符串錯誤,就像你拿著一把錯誤的鑰匙去開鎖,肯定打不開。如果數據庫文件路徑寫錯,或者遺漏了必要的參數,都會導致連接失敗。假設連接字符串寫成了string connectionString = "Data Source=nonexistent.db;Versinotallow=3;";,而實際數據庫文件并不存在,就會出現連接失敗的情況 。解決方法是仔細檢查連接字符串,確保數據庫文件路徑正確,參數完整無誤。

另外,權限不足也可能導致連接失敗。比如在 Windows 系統中,如果應用程序沒有足夠的權限訪問數據庫文件,就會被拒之門外。這時,需要檢查應用程序的權限設置,確保它對數據庫文件所在目錄有讀取和寫入的權限。

6.2 SQL 語法錯誤

編寫 SQL 語句時,稍有不慎就可能出現語法錯誤,比如關鍵字拼寫錯誤、標點符號使用不當等。像把SELECT寫成SELEC,或者在字符串值周圍忘記加引號,都會導致語法錯誤。例如string sql = "INSERT INTO Users (Name, Email) VALUES (張三, zhangsan@example.com)";,這里張三和zhangsan@example.com沒有加引號,就會引發語法錯誤。

解決這個問題,需要仔細檢查 SQL 語句的語法,確保關鍵字拼寫正確,標點符號使用規范。可以使用 SQLite 的官方文檔或在線語法檢查工具來輔助排查錯誤。

6.3 并發操作鎖表

SQLite 在同一時刻僅允許單個線程進行寫入操作,如果多個線程同時進行寫入,就可能導致鎖表問題,出現 “database is locked” 的錯誤。例如在一個多線程的應用程序中,多個線程同時執行插入數據的操作,就可能引發鎖表。

為了解決這個問題,可以使用事務和鎖機制來控制并發訪問。比如使用讀寫鎖(ReaderWriterLock),它可以允許多個線程同時進行讀取操作,但在寫入操作時會獨占鎖,確保數據的一致性和完整性。以下是一個簡單的示例代碼:

private static ReaderWriterLockSlim rwLock = new ReaderWriterLockSlim();public static void InsertData(string data){rwLock.EnterWriteLock();try{// 執行插入數據的操作using (SQLiteConnection conn = new SQLiteConnection(connectionString)){conn.Open();using (SQLiteCommand cmd = new SQLiteCommand("INSERT INTO TableName (Column) VALUES (@data)", conn)){cmd.Parameters.AddWithValue("@data", data);cmd.ExecuteNonQuery();}}}finally{rwLock.ExitWriteLock();}}

在這段代碼中,通過ReaderWriterLockSlim類創建了一個讀寫鎖rwLock。在插入數據的方法InsertData中,首先調用rwLock.EnterWriteLock()獲取寫鎖,這樣在獲取到鎖期間,其他線程無法獲取寫鎖,從而避免了并發寫入導致的鎖表問題。當數據插入操作完成后,通過rwLock.ExitWriteLock()釋放寫鎖,允許其他線程進行操作。

此外,還可以在 SQLite 的連接字符串中設置busy_timeout參數,讓數據庫在被鎖定時等待一段時間再重試,比如string connectionString = "Data Source=example.db;Versinotallow=3;busy_timeout=3000;";,這里設置等待時間為 3000 毫秒。同時,啟用 WAL(寫前日志)模式也能允許更高的并發訪問,可以通過執行PRAGMA journal_mode=WAL;命令來啟用 。

通過了解這些常見問題及解決方法,能幫助我們在使用 C# 和 SQLite 進行開發時,少走彎路,更高效地解決遇到的難題。

7. 總結與展望

在 C# 的開發世界里,SQLite 數據庫以其輕量級、易上手等特性,為我們提供了一種高效的數據存儲和管理方案。從搭建開發環境、引入 SQLite 支持,到創建數據庫連接,再到進行各種基本的數據操作,如創建表、插入、查詢、更新和刪除數據,每一步都是構建強大數據驅動應用的基石。

同時,我們還深入學習了一些進階技巧,如使用事務處理來確保數據的一致性和完整性,采用參數化查詢來防范 SQL 注入攻擊,通過創建索引和合理使用緩存來優化性能,以及完善的錯誤處理機制來保障應用的穩定性。在實戰案例中,我們將這些知識和技巧應用到學生管理系統的開發中,切實感受到了 C# 與 SQLite 結合的強大力量。

隨著技術的不斷發展,SQLite 也在持續演進。未來,它有望在性能優化、功能擴展等方面取得更大的突破。比如,在大數據處理方面,雖然 SQLite 目前主要適用于中小規模數據集,但也許在未來會有更好的解決方案來支持更大規模的數據存儲和分析;在安全性方面,可能會進一步加強加密和訪問控制等功能,以滿足日益增長的安全需求。希望大家能夠將所學的 C# 和 SQLite 知識運用到實際項目中,充分發揮它們的優勢,創造出更多優秀的應用。如果在學習和實踐過程中有任何疑問或心得,歡迎在留言區分享交流。

責任編輯:武曉燕 來源: 程序員編程日記
相關推薦

2023-11-24 11:11:08

Python數據庫

2013-02-20 14:54:03

C#.NETNDatabase

2023-12-13 08:22:45

SQLite關系型數據庫

2021-12-06 15:11:34

鴻蒙HarmonyOS應用

2021-08-31 14:58:52

鴻蒙HarmonyOS應用

2025-04-17 04:00:00

SQLite-WebSQLite數據庫

2022-08-31 12:48:48

TinyDBPython數據庫

2022-07-14 11:31:04

SQLToolsVScode數據庫

2024-09-20 18:02:42

C#數據庫SQLite

2010-12-20 09:44:36

SQLite.C#

2009-07-17 14:38:51

輕量級Swing組件

2009-07-14 18:05:28

輕量級Swing組件

2024-01-09 08:50:32

LiteDB數據庫NoSQL

2023-11-26 09:06:46

2009-01-19 09:28:42

JSONJavaScriptJSON結構

2011-08-30 14:15:34

QTSQLite數據庫

2022-05-30 07:31:38

SpringBoot搜索技巧

2024-02-28 08:06:17

2011-08-25 15:35:18

Lua游戲對象
點贊
收藏

51CTO技術棧公眾號

青青操在线视频| 强乱中文字幕av一区乱码| 天堂久久午夜av| 国产精品久久久久久久久图文区| 95av在线视频| 婷婷激情五月网| 91精品国产麻豆国产在线观看 | 久久久99久久| 91天堂在线观看| 国产成人一区二区三区影院在线| 精品视频免费在线观看| 日韩美一区二区三区| 国产综合免费视频| 男女羞羞视频在线观看| 国产免费久久精品| 国产欧美在线一区二区| 中文字幕91爱爱| 国产日产高清欧美一区二区三区| 久久久av一区| 在线免费看黄视频| 盗摄牛牛av影视一区二区| 欧美日韩一卡二卡三卡| 日本一区二区黄色| 七七成人影院| 亚洲视频一区二区免费在线观看| 欧美精彩一区二区三区| 丁香六月天婷婷| 国产一区欧美日韩| 国产精品视频免费在线| 久久久久久久久久免费视频| 最新欧美人z0oozo0| 中文字幕精品网| 亚洲国产日韩一区无码精品久久久| 国产精品极品| 欧美成人a视频| 亚洲一级片免费观看| 不卡亚洲精品| 欧美视频日韩视频在线观看| av之家在线观看| freexxx性亚洲精品| 亚洲精品高清在线观看| 午夜探花在线观看| 麻豆影院在线| 亚洲特黄一级片| 伊人久久青草| 国产午夜精品久久久久免费视| 中文字幕高清不卡| 日韩尤物视频| 国产www.大片在线| 国产欧美精品一区二区三区四区| 欧美一区二区三区在线播放| 日漫免费在线观看网站| 91美女蜜桃在线| 久久精品人成| 欧洲一级在线观看| 久久免费视频色| 欧美日韩电影一区二区三区| 女人天堂在线| 中文字幕av免费专区久久| 亚洲高清在线观看一区| 91这里只有精品| 中文字幕日本乱码精品影院| 中文字幕一区二区三区四区五区人 | 日韩avvvv在线播放| 国产精品久久久久久久一区探花 | 国产精品1区2区3区在线观看| 91色精品视频在线| www.精品久久| av不卡一区二区三区| 久久国产精品久久| 福利成人在线观看| 国产精品成人一区二区三区夜夜夜 | 亚洲资源中文字幕| 日日橹狠狠爱欧美超碰| 91精品一区二区三区蜜桃| 国产精品探花在线观看| 亚洲午夜久久久影院| 国产精品久久免费观看| 91偷拍一区二区三区精品| 欧美xxxx18性欧美| 国产第100页| 天堂一区二区在线| 成人激情视频免费在线| 二区三区在线视频| 国产亚洲综合色| 看全色黄大色大片| 白浆在线视频| 欧美日韩国产区一| av漫画在线观看| 精品无人区麻豆乱码久久久| 久久中文字幕国产| 欧美日韩精品区| 老司机精品视频一区二区三区| 国产日韩亚洲欧美| 人妻少妇精品无码专区| 国产日韩欧美在线一区| 亚洲精品少妇一区二区| 国产精品专区免费| 欧美一区二区三区电影| 中文字幕av网址| 天天综合亚洲| 欧洲亚洲妇女av| 国产三级按摩推拿按摩| 2024国产精品视频| 神马午夜伦理影院| 欧美7777| 日韩免费在线观看| 99久久精品免费视频| 国产一区二区三区四区老人| 国产精品黄色av| 人妻无码中文字幕| 日韩理论片在线| 欧美视频免费播放| 国产精品乱战久久久| 色偷偷噜噜噜亚洲男人的天堂| 国产网站在线看| 精品影视av免费| 日韩免费av电影| 欧美aaaaa性bbbbb小妇| 日韩精品一区二区三区在线 | 亚洲欧洲制服丝袜| 国产真实乱子伦| 国产精品白浆| 欧美大片免费观看在线观看网站推荐| 中文文字幕一区二区三三| 91一区在线观看| 午夜一区二区三区在线观看| av电影一区二区三区| 亚洲成av在线| 亚洲精品一区中文| 日韩精品成人一区| 国产99精品在线观看| 中文字幕欧美人与畜| 成人福利片在线| 夜夜嗨av色一区二区不卡| 欧美一区二区三区四| 成人ar影院免费观看视频| 国产精品一二三在线观看| 亚洲伦理久久| 精品国产一区二区三区久久狼黑人 | 最好看的中文字幕| 国产精品久久久久久影院8一贰佰| 国产999在线观看| 黄色网址在线播放| 色婷婷综合中文久久一本| 公侵犯人妻一区二区三区| 国产亚洲综合精品| 久久国产精品一区二区三区| heyzo在线播放| 亚洲国产精品久久久久| 日本亚洲欧美在线| 成人动漫视频在线| 国产av天堂无码一区二区三区| 好吊妞视频这里有精品| 国外色69视频在线观看| 日本xxxxwww| 岛国精品视频在线播放| 日本黄色录像片| 麻豆成人在线| 亚洲精品在线免费看| 日韩成人免费av| 久久中文久久字幕| 丰满岳乱妇国产精品一区| 天天综合色天天综合| 丰满少妇在线观看资源站| 另类av一区二区| 午夜精品视频在线观看一区二区 | 999在线观看免费大全电视剧| 超碰在线caoporn| 精品成人免费观看| 久久久精品免费看| 国产日韩精品一区| 九九热视频免费| 雨宫琴音一区二区在线| 久久伊人一区| 欧美高清影院| 欧美老女人在线视频| 日日夜夜精品免费| 一本色道久久加勒比精品| 波兰性xxxxx极品hd| 国产精品18久久久久久久网站| 黄页免费在线观看视频| 国语产色综合| 99伊人久久| 日韩不卡免费高清视频| 久久影视免费观看| 四虎影视精品成人| 欧美日韩一区二区三区四区| 国产精品日日夜夜| 中文字幕精品三区| 久久久久久久久久影视| 天堂一区二区在线免费观看| 久久免费一级片| 欧美码中文字幕在线| 成人午夜电影免费在线观看| 性感美女一区二区在线观看| 久久精品小视频| 欧美18xxxxx| 精品国精品国产| 五月婷婷视频在线| 一区二区三区**美女毛片| av手机在线播放| 成人动漫精品一区二区| 欧美美女性视频| 四虎影院观看视频在线观看| 91丨porny丨户外露出| 韩国日本在线视频| 欧美性久久久| 伊人久久大香线蕉成人综合网| 免费成人三级| 亚洲一区二区三区乱码aⅴ| 日韩a**中文字幕| 992tv在线成人免费观看| 好吊日视频在线观看| 国产香蕉97碰碰久久人人| 成人小说亚洲一区二区三区| 欧美猛男男办公室激情| 无码人妻精品一区二| 亚洲高清久久久| 紧身裙女教师波多野结衣| 国产网站一区二区| 一区二区三区免费在线观看视频 | 在线免费av一区| 日本三级一区二区| 亚洲va欧美va天堂v国产综合| 特一级黄色录像| 国产精品理论在线观看| 国产精久久一区二区三区| 99精品久久免费看蜜臀剧情介绍| 成人国产精品久久久| 国产毛片在线视频| 在线观看免费视频综合| 狠狠人妻久久久久久| 亚洲第一狼人社区| 国产一级特黄毛片| 一二三区精品视频| 精品一区二区三区人妻| 亚洲精品乱码久久久久久日本蜜臀| 欧美激情久久久久久久| 久久久99久久| 一级片久久久久| 中文字幕免费在线观看视频一区| 中国女人特级毛片| 国产精品女同一区二区三区| 蜜臀久久99精品久久久久久| 国产亚洲精品久| 91麻豆精品国产91久久综合| 日本一区二区三区视频视频| 久久成人激情视频| 日本一区二区不卡视频| 欧美日韩中文字幕视频| 久久精品欧美一区二区三区麻豆| 欧美特级黄色录像| 69精品国产久热在线观看| 日韩免费视频线观看| 99精品视频在线播放免费| 91精品国产91热久久久做人人| 国产伦子伦对白视频| 日韩亚洲欧美高清| 高h放荡受浪受bl| 日韩精品在线免费播放| 国产福利免费在线观看| 久久精品成人动漫| 青草视频在线免费直播 | 在线视频不卡一区二区三区| 999成人精品视频线3| 欧洲xxxxx| 中文亚洲字幕| 国产一区二区在线免费播放| 久久99精品久久久久久| 9191在线视频| 久久久久久免费毛片精品| 人妻熟人中文字幕一区二区| 亚洲精品欧美在线| 国产一级精品视频| 欧美性猛交xxxx乱大交退制版| 国产毛片毛片毛片毛片毛片| 亚洲成人999| 成人在线高清视频| 另类天堂视频在线观看| www.youjizz.com在线| 国产成人一区二| 秋霞一区二区三区| 免费av一区二区三区| 日韩av大片在线观看| 亚洲激情六月丁香| 中文字字幕在线中文| 欧美日韩成人激情| 色综合免费视频| 视频直播国产精品| 国产精品25p| 国产有码一区二区| 露出调教综合另类| 9999在线观看| 性欧美暴力猛交另类hd| 国产高清999| 久久精品欧美一区二区三区麻豆| 美女福利视频在线观看| 日本韩国一区二区三区视频| 精品二区在线观看| 亚洲天堂男人天堂| 超清av在线| 亚洲va欧美va国产综合剧情| 免费精品国产| 国产毛片久久久久久国产毛片| 蜜桃在线一区二区三区| 国产精品麻豆入口| 亚洲视频在线观看一区| 成人a v视频| 亚洲精品国产品国语在线| 动漫一区在线| 国产精品一区av| 婷婷综合福利| 日日摸日日碰夜夜爽无码| 久久99国产精品久久99| 韩国女同性做爰三级| 午夜精品一区在线观看| va视频在线观看| 色综久久综合桃花网| 成人爱爱网址| 国内一区在线| 激情欧美一区| 欧美激情第一区| 中文字幕中文字幕一区二区| 无码人妻精品一区二区蜜桃色欲| 亚洲国产精品一区二区三区| 伊人222成人综合网| 成人激情黄色网| 欧美国产一级| 午夜在线观看av| 国产视频一区在线观看| 天堂а√在线中文在线新版| 日韩激情片免费| 中文在线8资源库| 久久av一区二区| 国产欧美精品久久| 亚洲黄色在线网站| 精品久久久久久久久久久久久| 亚洲国产精品久久久久爰性色 | 欧美一区二区福利| 久久一区视频| 亚洲a v网站| 在线精品亚洲一区二区不卡| 久久久pmvav| 国产精品扒开腿做爽爽爽的视频| 美女久久99| 天堂av在线网站| 国产精品乱码妇女bbbb| 欧美久久久久久久久久久久久久| 精品一级毛片| 麻豆三级在线观看| 中文字幕一区二区三区四区不卡| 亚洲在线精品视频| 久久精品国产清自在天天线| 国产亚洲高清在线观看| 9191国产视频| 91原创在线视频| 欧美 亚洲 另类 激情 另类| 中日韩美女免费视频网站在线观看 | 不卡在线一区| 美女在线视频一区二区| 亚洲欧洲无码一区二区三区| 国产ts变态重口人妖hd| 久久久伊人日本| 欧美男男gaytwinkfreevideos| 日本老熟妇毛茸茸| 亚洲桃色在线一区| 天堂在线资源网| 国产精品成人免费视频| 91精品啪在线观看国产18| 精品人妻无码中文字幕18禁| 午夜影院在线观看欧美| 国产一级免费在线观看| 亚洲qvod图片区电影| 亚洲激情二区| 山东少妇露脸刺激对白在线| 91精品久久久久久久99蜜桃| 国产精品69xx| 日韩久久久久久久久久久久久| 国产一区二区三区免费在线观看| 久久高清免费视频| 尤物99国产成人精品视频| 精品视频在线播放一区二区三区 | 成熟的女同志hd| 亚洲精品国产精品自产a区红杏吧| 91超碰碰碰碰久久久久久综合| 强开小嫩苞一区二区三区网站| 99精品欧美一区二区蜜桃免费| 中文字幕乱码中文字幕| 欧美国产日韩免费| 精品一区不卡| aaaa黄色片| 欧美精品日日鲁夜夜添| 亚洲精品永久免费视频| 日韩视频在线观看视频| 91蜜桃免费观看视频| a级片在线播放| 国产精品久久久久久久久久久久久久 | 久久这里只有精品6| 国产日韩欧美一区二区东京热|