C# EF框架基礎(非MVC)使用筆記

DeMonnnnnn發表於2018-09-30

什麼是Entity Framework ?

微軟官方提供的ORM工具,ORM讓開發人員節省資料庫訪問的程式碼時間,將更多的時間放到業務邏輯層程式碼上。EF提供變更跟蹤、唯一性約束、惰性載入、查詢事物等。開發人員使用Linq語言,對資料庫操作如同操作Object物件一樣省事。
簡而言之:就是一個可以將資料庫與資料實體關聯的框架。

參考

微軟官方文件:Microsoft Docs

文章內容

  1. EF框架的基礎使用(非MVC下使用)
  2. 如何與資料庫建立連線
  3. 表與實體,列與屬性的關聯
  4. CRUD操作

資料庫連線

新增EF框架程式包

專案—>滑鼠右鍵—>管理NuGet程式包—>瀏覽—>輸入EntityFramework搜尋—>選擇第一個—>安裝

連線配置

如果專案中沒有Web.Config檔案,此處可以跳過,可以直接使用string直接連線(請看下文)。
在專案的Web.Config新增資料庫配置程式碼,如下所示:

<configuration>
	...
<connectionStrings>
    <add name="DeMonDBContext" connectionString="Data Source=(localdb)\ProjectsV13;database=DeMon;  
    	integrated security=True;uid=;pwd=;" providerName="System.Data.SqlClient" />
  </connectionStrings>
  ...
</configuration>

各引數詳解:

1.name 配置別名,標識
2.connectionString 連線字串,配置資訊

引數 解釋 備註
Data Source 伺服器地址 (此處為我的本地資料庫)
database 指定的資料庫
integrated security 是否連線安全 預設為true即可
uid 資料庫的使用者名稱 (因為是本地庫,所以為空)
pwd 資料庫的密碼 (因為時本地庫,所以為空)

3.providerName 資料庫連線驅動

資料庫型別 驅動
Aceess System.Data.OleDb
Oracle System.Data.OracleClient(Oracle.DataAccess.Client)
SQLite System.Data.SQLite
Sql System.Data.SqlClient

實體與表的關聯

EF框架的核心就是實體與資料表的關聯。

新建實體類

public class Movie {
        public int Id { get; set; }
        public string Name { get; set; }
    }

新建一個類繼承DbContext

DbContext有多個過載的構造方法,可以通過配置別名,標識或者連線字串與資料庫建立連線。

public class DeMonContext : DbContext {
	    //配置別名,標識
       //public DeMonContext() : base("DeMonDBContext") {}

	    //連線字串(注意\的轉義字元,即\\)
	  string str = "Data Source=(localdb)\\ProjectsV13;database=DeMon;integrated security=True;uid=;pwd=;";
        public DeMonContext() : base(str) {}
        
        //指定Movie實體與資料表關聯
        //如果存在資料表Movies(實體+s,複數命名),則使用
        //否則自動在資料庫下建立Movies資料表
        public DbSet<Movie> Movies { get; set; }
}

去除複數命名

如果不想以複數命名的格式。
在上面程式碼新增如下程式碼。

public class DeMonContext : DbContext {
         ...
        protected override void OnModelCreating(DbModelBuilder modelBuilder) {
            modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();//去除複數命名
        }
    }

實體名與資料庫表名不一致?

如果資料表已經存在,且命名很長或者與我們習慣的不一致。
在上面程式碼新增如下程式碼。

public class DeMonContext : DbContext {
         ...
        protected override void OnModelCreating(DbModelBuilder modelBuilder) {
            ...
            //指定MovieDetail實體與資料表Movie_Detail關聯
            modelBuilder.Entity<MovieDetail>().ToTable("Movie_Detail");//實體關聯對應的表名
        }
    }

實體屬性與表欄位不一致?

使用column特性的建構函式,對映欄位到實體屬性。

public class MovieDetail {
        public int ID { get; set; }
        public string Describe { get; set; }
        //指定MovieId與表欄位Movie_Id關聯
        [Column("Movie_Id")]
        public int MovieId { get; set; }
    }

CRUD

講完了配置,連線,關聯。接下來講一下CRUD(增,讀,改,刪)操作。

初始化

宣告一個資料庫連線的上下文物件。

//建立一個EF資料上下文物件
private DeMonContext db = new DeMonContext();

public string CreateMovie(string Name) {
	        //將要新增的資料,封裝成物件
            Movie movie = new Movie { Name = Name};
            db.Movies.Add(movie);
            //當呼叫SaveChanges()時,EF會遍歷所有的代理類物件,並根據標誌生成相應的sql語句
            db.SaveChanges();
            return "新增成功!";
        }
public string CreateMovie(string Name) {
            Movie movie = new Movie { Name = Name };
            //標記為Add狀態
            db.Entry(movie).State = EntityState.Added;
            db.SaveChanges();
            return "新增成功!";
        }

讀(查詢)

1.獲取全部資料

public string GetMovies() {
            var list = db.Movies.ToList();
            //將物件轉為Json
            //需要新增NewtonSoft.Json程式包
            return JsonConvert.SerializeObject(list);
        }

2.主鍵(Id)查詢

public string GetMovies(int id) {
            var list = db.Movies.Find(id);
            return JsonConvert.SerializeObject(list);
        }

3.非主鍵查詢
通過Name欄位值為Name的查詢。


        public string GetMovies(string Name) {
            var list = db.Movies.Where(x=>x.Name == Name).ToList();
            return JsonConvert.SerializeObject(list);
        }

改(更新)

1.根據主鍵(Id)修改Name欄位

public string UpdateMovieById(int id, string Name) {
            Movie movie = new Movie { Id = id, Name = Name };
              //標記為修改狀態
            db.Entry(movie).State = EntityState.Modified;
            db.SaveChanges();
            return "修改成功!";
        }

2.根據非主鍵欄位修改
將Name欄位值為Name1的修改為Name2。

public string UpdateMovieByName(string Name1, string Name2) {
            //先根據Name欄位查詢
            var list = db.Movies.Where(x => x.Name == Name1).ToList();
            foreach (Movie movie in list) {
                movie.Name = Name2;
                db.Entry(movie).State = EntityState.Modified;
            }
            db.SaveChanges();
            return "修改成功!";
        }

1.根據的主鍵(Id)刪除

public string DeleteMovieById(int id) {
            Movie movie = new Movie { Id = id };
            //標記為刪除狀態
            db.Entry(movie).State = EntityState.Deleted;
            db.SaveChanges();
            return "刪除成功!";
        }

public string DeleteMovieById(int id) {
            Movie movie = new Movie { Id = id };
            //將要刪除的物件附加到EF容器中
            db.Movies.Attach(movie);
            db.Movies.Remove(movie);
            db.SaveChanges();
            return "刪除成功!";
        }
public string DeleteMovieById(int id) {
            //可以先Find實體再刪除
            Movie movie = db.Movies.Find(id);
            db.Movies.Remove(movie);
            db.SaveChanges();
            return "刪除成功!";
        }

2.根據非主鍵刪除
刪除Name欄位值為Name的。

 public string DeleteMovieByName(string Name) {
            //先根據Name欄位查詢
            var list = db.Movies.Where(x => x.Name == Name).ToList();
            foreach (Movie movie in list) {
                db.Movies.Remove(movie);
            }
            db.SaveChanges();
            return "刪除成功!";
        }

相關文章