为什么将更改保存到数据库失败?

我在控制台应用程序中有以下C#代码。

每当我debugging应用程序并运行query1(它向数据库中插入一个新值),然后运行query2(它显示数据库中的所有条目)时,我可以看到我插入的新条目清晰。 但是,当我closures应用程序并检查数据库中的表(在Visual Studio中)时,它不见了。 我不知道为什么它没有保存。

using System; using System.Collections.Generic; using System.Data.Entity; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Data.SqlServerCe; using System.Data; namespace ConsoleApplication1 { class Program { static void Main(string[] args) { try { string fileName = "FlowerShop.sdf"; string fileLocation = "|DataDirectory|\\"; DatabaseAccess dbAccess = new DatabaseAccess(); dbAccess.Connect(fileName, fileLocation); Console.WriteLine("Connected to the following database:\n"+fileLocation + fileName+"\n"); string query = "Insert into Products(Name, UnitPrice, UnitsInStock) values('NewItem', 500, 90)"; string res = dbAccess.ExecuteQuery(query); Console.WriteLine(res); string query2 = "Select * from Products"; string res2 = dbAccess.QueryData(query2); Console.WriteLine(res2); Console.ReadLine(); } catch (Exception e) { Console.WriteLine(e); Console.ReadLine(); } } } class DatabaseAccess { private SqlCeConnection _connection; public void Connect(string fileName, string fileLocation) { Connect(@"Data Source=" + fileLocation + fileName); } public void Connect(string connectionString) { _connection = new SqlCeConnection(connectionString); } public string QueryData(string query) { _connection.Open(); using (SqlCeDataAdapter da = new SqlCeDataAdapter(query, _connection)) using (DataSet ds = new DataSet("Data Set")) { da.Fill(ds); _connection.Close(); return ds.Tables[0].ToReadableString(); // a extension method I created } } public string ExecuteQuery(string query) { _connection.Open(); using (SqlCeCommand c = new SqlCeCommand(query, _connection)) { int r = c.ExecuteNonQuery(); _connection.Close(); return r.ToString(); } } } 

编辑:忘了提及我正在使用SQL Server Compact Edition 4和VS2012 Express。

这是一个相当普遍的问题。 您使用| DataDirectory | replacestring。 这意味着,在Visual Studio环境中debugging应用程序时,应用程序使用的数据库位于项目的子文件夹BIN\DEBUG文件夹(或x86变体)中。 而且这种方式很有效,因为连接到数据库和进行更新操作时都没有任何错误。

但是,然后退出debugging会话,并通过Visual Studio Server Explorer查看数据库。 该窗口有不同的连接string(可能指向项目文件夹中的数据库副本)。 你search你的表格,你没有看到变化。

然后问题变得更糟。 您重新启动VS以检查您的应用程序,但是您的数据库文件列在您的项目文件之间,并且“ Copy to Output directory的属性设置为Copy Always 。 此时,Visual Studio将原始数据库文件从项目文件夹复制到输出文件夹(BIN \ DEBUG),因此以前的更改将丢失。
现在,您的应用程序也不会看到之前所做的更改。 (现在,你也可以听到各种丑陋的话)

您可以停止此问题更改属性Copy To Output Directory Copy If NewerNever Copy 。 你也可以在服务器资源pipe理器中更新连接string,查看数据库的工作副本或创build第二个连接。 第一个仍然指向项目文件夹中的数据库,而第二个指向BIN \ DEBUG文件夹中的数据库。 通过这种方式,您可以保留原始数据库以便部署和架构更改,而通过第二个连接,您可以查看编码工作的有效结果。

编辑 MS-Access数据库用户的特别警告。 查看你的表的简单行为改变了你的数据库的修改date如果你不写或改变任何东西。 所以Copy if Newer标志Copy if Newer并且数据库文件被复制到输出目录。 与Access更好地使用Copy Never

在debugging会话中提交更改/保存更改是SQL CE论坛中熟悉的主题。 这是绊倒了不less人。 我将发布链接到下面的源文章,但我想贴上似乎得到最好的结果给大多数人的答案:


你有几个select来改变这种行为。 如果您的sdf文件是您的项目内容的一部分,这将影响数据如何持久。 请记住,当你debugging时,如果在bin / debug文件夹中,你的项目的所有输出(包括sdf)。

  • 您可以决定不要将sdf文件作为项目的一部分,并pipe理文件位置运行时。

  • 如果您正在使用“如果更新”,则对数据库所做的项目更改将覆盖任何运行时/debugging更改。

  • 如果您正在使用“不要复制”,则必须在代码中指定位置(如程序运行的上方两个级别)。

  • 如果您有“始终复制”,则运行时所做的任何更改将始终被覆盖


回答来源

这里有一些进一步的讨论和如何文档的链接 。