Windows Phone的本地數據庫SQL Server CE是7.1版本即芒果更新的新特性,所以你要在應用程序中使用SQL Server CE數據庫必須使用Windows Phone 7.1的API才行 。這個數據庫是用Linq來執行查詢等操作。
我們現在用數據庫來保存城市的數據,包括所屬省份,城市名稱,城市代碼。在程序中我們只做了簡單的插入和查詢,需要詳細的數據庫操作可以參考
http://windowsphonegeek.com/tips/Windows-Phone-Mango-Local-Database(SQL-CE)-Introduction或者MSDN。
現在回到工程上,先創建一個數據表,CityInfoTable.
在工程上右鍵---添加--類。命名為CityInfoTable.cs ,接着添加引用。工程----右鍵---添加引用。
找到System.Data.Linq.點擊確定。
接着在CityInfoTable.cs添加命名空間。
- using System.Data.Linq.Mapping;
- using System.ComponentModel;
using System.Data.Linq.Mapping; using System.ComponentModel;
然后在CItyInfoTable這個數據表定義主鍵等屬性,給出完整的CityInfoTable.cs代碼
- using System;
- using System.Net;
- using System.Windows;
- using System.Windows.Controls;
- using System.Windows.Documents;
- using System.Windows.Ink;
- using System.Windows.Input;
- using System.Windows.Media;
- using System.Windows.Media.Animation;
- using System.Windows.Shapes;
- using System.Data.Linq.Mapping;
- using System.ComponentModel;
- namespace WeatherForecast
- {
- [Table]//把CItyInfoTable定義為表
- public class CityInfoTable
- {
- //定義表的自增ID。設置為主鍵
- private int _cityInfoid;
using System; using System.Net; using System.Windows; using System.Windows.Controls; using System.Windows.Documents; using System.Windows.Ink; using System.Windows.Input; using System.Windows.Media; using System.Windows.Media.Animation; using System.Windows.Shapes; using System.Data.Linq.Mapping; using System.ComponentModel; namespace WeatherForecast { [Table]//把CItyInfoTable定義為表 public class CityInfoTable { //定義表的自增ID。設置為主鍵 private int _cityInfoid;
- <span style="white-space: pre;"> </span>//Column這個是定義一個成員為表字段。如果沒有這個,那么這個成員不是字段
//Column這個是定義一個成員為表字段。如果沒有這個,那么這個成員不是字段
- [Column(IsPrimaryKey = true, IsDbGenerated = true,
- DbType = "INT NOT NULL Identity", CanBeNull = false, AutoSync = AutoSync.OnInsert)]
- public int CityInfoid
- {
- get
- {
- return _cityInfoid;
- }
- set
- {
- _cityInfoid = value;
- }
- }
- //定義省份名稱:
- private string _province;
- [Column]
- public string Province
- {
- get
- {
- return _province;
- }
- set
- {
- _province = value;
- }
- }
- //定義城市名稱
- private string _cityName;
- [Column]
- public string CityName
- {
- get
- {
- return _cityName;
- }
- set
- {
- _cityName = value;
- }
- }
- //定義城市代碼
- private string _cityCode;
- [Column]
- public string CityCode
- {
- get
- {
- return _cityCode;
- }
- set
- {
- _cityCode = value;
- }
- }
- }
- }
[Column(IsPrimaryKey = true, IsDbGenerated = true, DbType = "INT NOT NULL Identity", CanBeNull = false, AutoSync = AutoSync.OnInsert)] public int CityInfoid { get { return _cityInfoid; } set { _cityInfoid = value; } } //定義省份名稱: private string _province; [Column] public string Province { get { return _province; } set { _province = value; } } //定義城市名稱 private string _cityName; [Column] public string CityName { get { return _cityName; } set { _cityName = value; } } //定義城市代碼 private string _cityCode; [Column] public string CityCode { get { return _cityCode; } set { _cityCode = value; } } } }
現在再定義一個數據庫。工程---右鍵---新建類,命名為CityDataContext.cs。
添加命名空間。
- using System.Data.Linq;
using System.Data.Linq;
然后讓這個類繼承於DataContext。
給出CityDataContext.cs的完整代碼:
- using System;
- using System.Net;
- using System.Windows;
- using System.Windows.Controls;
- using System.Windows.Documents;
- using System.Windows.Ink;
- using System.Windows.Input;
- using System.Windows.Media;
- using System.Windows.Media.Animation;
- using System.Windows.Shapes;
- using System.Data.Linq;
- namespace WeatherForecast
- {
- /// <summary>
- /// 定義一個數據庫
- /// </summary>
- public class CityDataContext : DataContext
- {
- //定義數據庫連接字符串
- public static string connectionString = "Data Source=isostore:/CityInfo.sdf";
- //// 傳遞數據庫連接字符串到DataContext基類
- public CityDataContext(string connectionString) : base(connectionString) { }
- //定義一個數據表,如果有多個數據表也可以繼續添加為成員變量
- public Table<CityInfoTable> CityInfos
- {
- get
- {
- return this.GetTable<CityInfoTable>();
- }
- }
- }
- }
using System; using System.Net; using System.Windows; using System.Windows.Controls; using System.Windows.Documents; using System.Windows.Ink; using System.Windows.Input; using System.Windows.Media; using System.Windows.Media.Animation; using System.Windows.Shapes; using System.Data.Linq; namespace WeatherForecast { /// <summary> /// 定義一個數據庫 /// </summary> public class CityDataContext : DataContext { //定義數據庫連接字符串 public static string connectionString = "Data Source=isostore:/CityInfo.sdf"; //// 傳遞數據庫連接字符串到DataContext基類 public CityDataContext(string connectionString) : base(connectionString) { } //定義一個數據表,如果有多個數據表也可以繼續添加為成員變量 public Table<CityInfoTable> CityInfos { get { return this.GetTable<CityInfoTable>(); } } } }
到這里,數據庫算是寫好了。新手肯定會有疑問,沒有看到什么數據庫。也沒在工程里面看到什么SDF文件。
因為,我們要在程序構建的時候用代碼創建數據庫,由上面的連接字符串可以知道,數據庫創建后放在Isolatedstorage里面,創建這個在App.xaml里面的Launching事件里面實現。
可以在這個事件里添加這樣的代碼創建數據庫:
- using (CityDataContext db = new CityDataContext(CityDataContext.connectionString))
- {
- if (db.DatabaseExists() == false)
- {
- //創建一個數據庫
- db.CreateDatabase();
- <span style="white-space: pre;"> </span>}
- <span style="white-space: pre;"> </span>}
using (CityDataContext db = new CityDataContext(CityDataContext.connectionString))
{
if (db.DatabaseExists() == false)
{
//創建一個數據庫
db.CreateDatabase();
}
}
這個我們暫時不做。現在我們先添加一個城市信息的XML文件。下載:http://dl.dbank.com/c02jod17n0
復制這個文件。在工程上面右鍵--粘貼。就把這個citycode.xml文件加入到了工程上。
接下來就做XML解析。用的XDocument類。這里只是簡單應用了下。
我們要在App.xaml里面的Launching 事件添加代碼。因為我們要在初次運行程序的時候要建立數據庫,並且解析citycode.xml的數據添加到數據庫里面。
要讀取工程里面的文件。要用到的是Application.GetResourceStream.這個函數只能讀取資源文件。那么我們要將citycode.xml文件的Building屬性改為Resource。
操作方法:選擇citycode.xml-----點擊屬性---生成操作(Building)改為Resource。
要使用XDocument類,需要添加引用。添加System.Xml.Linq。已經添加很多次引用了,那么這次就不詳細說怎么操作了。
在App.xaml.cs里面添加命名空間;
- using System.Windows.Resources;
- using System.IO;
- using System.Xml.Linq;
using System.Windows.Resources; using System.IO; using System.Xml.Linq;
添加成員函數:
- private void CreatDB()
- {
- using (CityDataContext db = new CityDataContext(CityDataContext.connectionString))
- {
- if (db.DatabaseExists() == false)
- {
- //創建一個數據庫
- db.CreateDatabase();
- //讀取資源文件。文件為XML格式。這個文件的Building屬性為Resource
- StreamResourceInfo sri = Application.GetResourceStream(new Uri("/WeatherForecast;component/citycode.xml",
- UriKind.Relative));
- //讀取所以數據保存到String類型的result中
- string result;
- using (StreamReader sr = new StreamReader(sri.Stream))
- {
- result = sr.ReadToEnd();
- }
- //用XDocument類解析數據
- XDocument doc = XDocument.Parse(result);
- //解析數據並且存入數據庫
- foreach (XElement item in doc.Descendants("root").Nodes())
- {
- //由文件中的數據可以知道。我們需要的數據在那么兩個節點。Descendants就是尋找子節點。
- string province = item.Attribute("data").Value;
- foreach (XElement itemnode in item.Descendants("city"))
- {
- string cityname = itemnode.Element("cityname").Value;
- string cityid = itemnode.Element("cityid").Value;
- //把數據存入數據庫
- CityInfoTable cityInfo = new CityInfoTable();
- cityInfo.CityCode = cityid;
- cityInfo.Province = province;
- cityInfo.CityName = cityname;
- db.CityInfos.InsertOnSubmit(cityInfo);
- }
- }
- //數據庫提交更新
- db.SubmitChanges();
- }
- }
- }
private void CreatDB() { using (CityDataContext db = new CityDataContext(CityDataContext.connectionString)) { if (db.DatabaseExists() == false) { //創建一個數據庫 db.CreateDatabase(); //讀取資源文件。文件為XML格式。這個文件的Building屬性為Resource StreamResourceInfo sri = Application.GetResourceStream(new Uri("/WeatherForecast;component/citycode.xml", UriKind.Relative)); //讀取所以數據保存到String類型的result中 string result; using (StreamReader sr = new StreamReader(sri.Stream)) { result = sr.ReadToEnd(); } //用XDocument類解析數據 XDocument doc = XDocument.Parse(result); //解析數據並且存入數據庫 foreach (XElement item in doc.Descendants("root").Nodes()) { //由文件中的數據可以知道。我們需要的數據在那么兩個節點。Descendants就是尋找子節點。 string province = item.Attribute("data").Value; foreach (XElement itemnode in item.Descendants("city")) { string cityname = itemnode.Element("cityname").Value; string cityid = itemnode.Element("cityid").Value; //把數據存入數據庫 CityInfoTable cityInfo = new CityInfoTable(); cityInfo.CityCode = cityid; cityInfo.Province = province; cityInfo.CityName = cityname; db.CityInfos.InsertOnSubmit(cityInfo); } } //數據庫提交更新 db.SubmitChanges(); } } }
在Launching事件添加如下代碼:
- CreatDB();
CreatDB();
這樣,我們就能在第一次執行程序的時候,創建數據庫,並且解析XML數據,把城市信息存入數據庫。
那么還是測試下吧。
在MainPage的Loaded事件中測試,查詢北京的數據,彈窗顯示。
在Loaded事件中添加如下代碼:
- using (CityDataContext db = new CityDataContext(CityDataContext.connectionString))
- {
- IQueryable<CityInfoTable> queries =
- from c in db.CityInfos where c.Province == "北京" && c.CityName == "北京" select c;
- MessageBox.Show(queries.First().CityName + queries.First().CityCode);
- }
using (CityDataContext db = new CityDataContext(CityDataContext.connectionString)) { IQueryable<CityInfoTable> queries = from c in db.CityInfos where c.Province == "北京" && c.CityName == "北京" select c; MessageBox.Show(queries.First().CityName + queries.First().CityCode); }
成功!那么就把剛才添加的測試代碼注釋掉吧。。。
PS:調試數據庫,XML解析的時候我可是相當糾結了。都是心理默念不要出錯,不要出錯。。。
因為出錯的話,數據庫是建立了。但是數據八成沒有加入進去。要刪除數據庫,就要重啟模擬器了。因為重啟模擬器IsolatedStorage里面的數據就沒了。但是,我的機子如果重啟模擬器的話,沒有個五六分鍾不行。。多出錯幾次半小時都沒了。。
提示:如果在建立數據庫處出錯了。記得重啟模擬器再調試。