首页 > 代码库 > SQLCE使用

SQLCE使用

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添加命名空间。

 

[csharp] view plaincopyprint?
  1. using System.Data.Linq.Mapping; 
  2. using System.ComponentModel; 
using System.Data.Linq.Mapping;using System.ComponentModel;

然后在CItyInfoTable这个数据表定义主键等属性,给出完整的CityInfoTable.cs代码

 

 

[csharp] view plaincopyprint?
  1. using System; 
  2. using System.Net; 
  3. using System.Windows; 
  4. using System.Windows.Controls; 
  5. using System.Windows.Documents; 
  6. using System.Windows.Ink; 
  7. using System.Windows.Input; 
  8. using System.Windows.Media; 
  9. using System.Windows.Media.Animation; 
  10. using System.Windows.Shapes; 
  11. using System.Data.Linq.Mapping; 
  12. using System.ComponentModel; 
  13.  
  14.  
  15. namespace WeatherForecast 
  16.     [Table]//把CItyInfoTable定义为表 
  17.     public class CityInfoTable 
  18.     { 
  19.         //定义表的自增ID。设置为主键 
  20.         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;
[csharp] view plaincopyprint?
  1. <span style="white-space: pre;">    </span>//Column这个是定义一个成员为表字段。如果没有这个,那么这个成员不是字段 
	//Column这个是定义一个成员为表字段。如果没有这个,那么这个成员不是字段
[csharp] view plaincopyprint?
  1.         [Column(IsPrimaryKey = true, IsDbGenerated = true, 
  2.             DbType = "INT NOT NULL Identity", CanBeNull = false, AutoSync = AutoSync.OnInsert)] 
  3.         public int CityInfoid 
  4.         { 
  5.             get 
  6.             { 
  7.                 return _cityInfoid; 
  8.             } 
  9.             set 
  10.             { 
  11.                 _cityInfoid = value; 
  12.             } 
  13.         } 
  14.  
  15.  
  16.         //定义省份名称: 
  17.         private string _province; 
  18.         [Column] 
  19.         public string Province 
  20.         { 
  21.             get 
  22.             { 
  23.                 return _province; 
  24.             } 
  25.             set 
  26.             { 
  27.                 _province = value; 
  28.             } 
  29.         } 
  30.  
  31.         //定义城市名称 
  32.         private string _cityName; 
  33.  
  34.         [Column] 
  35.         public string CityName 
  36.         { 
  37.             get 
  38.             { 
  39.                 return _cityName; 
  40.             } 
  41.             set 
  42.             { 
  43.                 _cityName = value; 
  44.             } 
  45.         } 
  46.  
  47.         //定义城市代码 
  48.         private string _cityCode; 
  49.  
  50.         [Column] 
  51.         public string CityCode 
  52.         { 
  53.             get 
  54.             { 
  55.                 return _cityCode; 
  56.             } 
  57.             set 
  58.             { 
  59.                 _cityCode = value; 
  60.             } 
  61.         } 
  62.  
  63.     } 
        [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。

 

添加命名空间。

 

[csharp] view plaincopyprint?
  1. using System.Data.Linq; 
using System.Data.Linq;

然后让这个类继承于DataContext。

 

给出CityDataContext.cs的完整代码:

 

[csharp] view plaincopyprint?
  1. using System; 
  2. using System.Net; 
  3. using System.Windows; 
  4. using System.Windows.Controls; 
  5. using System.Windows.Documents; 
  6. using System.Windows.Ink; 
  7. using System.Windows.Input; 
  8. using System.Windows.Media; 
  9. using System.Windows.Media.Animation; 
  10. using System.Windows.Shapes; 
  11. using System.Data.Linq; 
  12.  
  13.  
  14. namespace WeatherForecast 
  15.     /// <summary> 
  16.     /// 定义一个数据库 
  17.     /// </summary> 
  18.     public class CityDataContext : DataContext 
  19.     { 
  20.         //定义数据库连接字符串 
  21.         public static string connectionString = "Data Source=isostore:/CityInfo.sdf"; 
  22.  
  23.         //// 传递数据库连接字符串到DataContext基类 
  24.         public CityDataContext(string connectionString) : base(connectionString) { } 
  25.  
  26.  
  27.         //定义一个数据表,如果有多个数据表也可以继续添加为成员变量 
  28.         public Table<CityInfoTable> CityInfos 
  29.         { 
  30.             get 
  31.             { 
  32.                 return this.GetTable<CityInfoTable>(); 
  33.             } 
  34.         } 
  35.     } 
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事件里面实现。

可以在这个事件里添加这样的代码创建数据库:

 

[csharp] view plaincopyprint?
  1. using (CityDataContext db = new CityDataContext(CityDataContext.connectionString)) 
  2.             { 
  3.  
  4.                 if (db.DatabaseExists() == false) 
  5.                 { 
  6.  
  7.                     //创建一个数据库 
  8.  
  9.                     db.CreateDatabase(); 
  10. <span style="white-space: pre;">        </span>} 
  11. <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里面添加命名空间;

 

[csharp] view plaincopyprint?
  1. using System.Windows.Resources; 
  2. using System.IO; 
  3. using System.Xml.Linq; 
using System.Windows.Resources;using System.IO;using System.Xml.Linq;

添加成员函数:

 

 

[csharp] view plaincopyprint?
  1. private void CreatDB() 
  2.        { 
  3.            using (CityDataContext db = new CityDataContext(CityDataContext.connectionString)) 
  4.            { 
  5.  
  6.                if (db.DatabaseExists() == false) 
  7.                { 
  8.  
  9.                    //创建一个数据库 
  10.  
  11.                    db.CreateDatabase(); 
  12.                    //读取资源文件。文件为XML格式。这个文件的Building属性为Resource 
  13.                    StreamResourceInfo sri = Application.GetResourceStream(new Uri("/WeatherForecast;component/citycode.xml", 
  14.                        UriKind.Relative)); 
  15.                    //读取所以数据保存到String类型的result中 
  16.                    string result; 
  17.                    using (StreamReader sr = new StreamReader(sri.Stream)) 
  18.                    { 
  19.                        result = sr.ReadToEnd(); 
  20.                    } 
  21.  
  22.                    //用XDocument类解析数据 
  23.                    XDocument doc = XDocument.Parse(result); 
  24.  
  25.                    //解析数据并且存入数据库 
  26.                    foreach (XElement item in doc.Descendants("root").Nodes()) 
  27.                    { 
  28.                        //由文件中的数据可以知道。我们需要的数据在那么两个节点。Descendants就是寻找子节点。 
  29.                        string province = item.Attribute("data").Value; 
  30.                        foreach (XElement itemnode in item.Descendants("city")) 
  31.                        { 
  32.                            string cityname = itemnode.Element("cityname").Value; 
  33.                            string cityid = itemnode.Element("cityid").Value; 
  34.                            //把数据存入数据库 
  35.                            CityInfoTable cityInfo = new CityInfoTable(); 
  36.                            cityInfo.CityCode = cityid; 
  37.                            cityInfo.Province = province; 
  38.                            cityInfo.CityName = cityname; 
  39.                            db.CityInfos.InsertOnSubmit(cityInfo); 
  40.                        } 
  41.                    } 
  42.                    //数据库提交更新 
  43.                    db.SubmitChanges(); 
  44.                } 
  45.  
  46.            } 
  47.        } 
 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事件添加如下代码:

 

 

[csharp] view plaincopyprint?
  1. CreatDB(); 
CreatDB();

这样,我们就能在第一次执行程序的时候,创建数据库,并且解析XML数据,把城市信息存入数据库。

 

 

那么还是测试下吧。

在MainPage的Loaded事件中测试,查询北京的数据,弹窗显示。

在Loaded事件中添加如下代码:

 

[csharp] view plaincopyprint?
  1. using (CityDataContext db = new CityDataContext(CityDataContext.connectionString)) 
  2.             { 
  3.                 IQueryable<CityInfoTable> queries = 
  4.                     from c in db.CityInfos where c.Province == "北京" && c.CityName == "北京" select c; 
  5.                 MessageBox.Show(queries.First().CityName + queries.First().CityCode); 
  6.             } 
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里面的数据就没了。但是,我的机子如果重启模拟器的话,没有个五六分钟不行。。多出错几次半小时都没了。。

提示:如果在建立数据库处出错了。记得重启模拟器再调试。