C# 从SQL表记录创建.DBF文件

C# 从SQL表记录创建.DBF文件,c#,.net,dbf,C#,.net,Dbf,我想从SQL表记录创建一个.DBF文件 例如,如果SQL中有一个名为CountryMaster的表,它有5列: ID整数标识(1,1) 名称varchar(100) 详细信息varchar(200) 状态位 创建日期时间 它有100行 如何从C#导出这些标题为.DBF文件的记录 注意:创建的.DBF文件大小必须非常紧凑。您可以查看结构并编写自己的代码,但我已经完成了实现,并且已经使用了多年。在这里你可以找到它 如何使用图书馆 在名为DbfFile.cs的文件中有一些write方法。你可以使用其

我想从SQL表记录创建一个
.DBF
文件

例如,如果SQL中有一个名为
CountryMaster
的表,它有5列:

  • ID整数标识(1,1)
  • 名称varchar(100)
  • 详细信息varchar(200)
  • 状态位
  • 创建日期时间
  • 它有100行

    如何从C#导出这些标题为
    .DBF
    文件的记录

    注意:创建的
    .DBF
    文件大小必须非常紧凑。

    您可以查看结构并编写自己的代码,但我已经完成了实现,并且已经使用了多年。在这里你可以找到它


    如何使用图书馆 在名为DbfFile.cs的文件中有一些write方法。你可以使用其中任何一种。我会解释其中一些:

    第一种写入方法 将
    DataTable
    另存为dbf文件:

    static void Write(string fileName, System.Data.DataTable table, Encoding encoding)
    
    • fileName
      :是要保存
      .dbf
      输出文件的位置
    • :是您从SQL Server或任何其他来源读取的数据
    • 编码
      :保存字符串数据时要使用的编码
    第二种写入方法 将
    列表
    保存到dbf文件中

    static void Write<T>(string fileName,
                                        List<T> values,
                                        List<Func<T, object>> mapping,
                                        List<DbfFieldDescriptor> columns,
                                        Encoding encoding)
    
    现在,您可以将
    列表
    保存到dbf文件中,如下所示:

    var idColumn = DbfFieldDescriptors.GetIntegerField("Id");
    var nameColumn = DbfFieldDescriptors.GetStringField("Name");
    var columns = new List<DbfFieldDescriptor>() { idColumn, nameColumn };
    
    Func<MyClass, object> mapId = myClass => myClass.Id;
    Func<MyClass, object> mapName = myClass => myClass.Name;
    var mapping = new List<Func<MyClass, object>>() { mapId, mapName };
    
    List<MyClass> values = new List<MyClass>();
    values.Add(new MyClass() { Id = 1, Name = "name1" });
    
    DbfFileFormat.Write(@"C:\yourFile.dbf", values, mapping, columns, Encoding.ASCII);
    
    var idColumn=dbffieldscriptors.GetIntegerField(“Id”);
    var nameColumn=DbfFieldDescriptors.GetStringField(“名称”);
    var columns=new List(){idColumn,nameColumn};
    Func mapId=myClass=>myClass.Id;
    Func mapName=myClass=>myClass.Name;
    var mapping=new List(){mapId,mapName};
    列表值=新列表();
    Add(new MyClass(){Id=1,Name=“name1”});
    Write(@“C:\yourFile.dbf”,值,映射,列,编码.ASCII);
    

    还可以使用此库读取dbf文件,而代码不需要 依赖Microsoft.Jet.OLEDB或其他任何东西


    享受它。

    您需要的大部分信息都可以在上看到,因为它显示了如何在创建.dbf文件时创建表并向其中插入值。您需要对指定的字段进行一些修改,但该页面描述了您需要的所有内容。

    我想提供帮助。然而,对于VPF,我坚持使用OLEDB的普通流程

    创建表DBF

    这可能是.DBF的创建表脚本

    CREATE TABLE "C:\test.dbf" ([ID] Numeric(18,0), [Name] Char(100) NULL, [Details] Char(200) NULL, [Status] Logical NULL, [CreateDate] DATETIME NULL)
    
    然后,您可以从下面使用的OLEDB脚本调用此脚本

        string vpfScript = "CREATE TABLE \"C:\test.dbf\" ([ID] Numeric(18,0), [Name] Char(100) NULL, [Details] Char(200) NULL, [Status] Logical NULL, [CreateDate] DATETIME NULL)";
        string connectionString = @"Provider=VFPOLEDB.1;Data Source=C:\test.dbf";
        OleDbConnection connection = new OleDbConnection(connectionString);
    
        using (OleDbCommand scriptCommand = connection.CreateCommand())
        {
             connection.Open();
             scriptCommand.CommandType = CommandType.StoredProcedure;
             scriptCommand.CommandText = "ExecScript";
             scriptCommand.Parameters.Add("myScript", OleDbType.Char).Value = vfpScript;
             scriptCommand.ExecuteNonQuery();
        }
    
    导入表中的行

    要导入DBF表中的行,它不像我们在其他数据库中使用的常规SQL脚本那样远

        string vpfScript = "INSERT INTO \"C:\test.dbf\" ([ID], [Name], [Details], [Status], [CreateDate]) VALUES (1,'test john','test details',.t.,{^2015-09-15)";
        string connectionString = @"Provider=VFPOLEDB.1;Data Source=C:\test.dbf";
        OleDbConnection connection = new OleDbConnection(connectionString);
    
        using (OleDbCommand scriptCommand = connection.CreateCommand())
        {
            connection.Open();
            scriptCommand.CommandType = CommandType.StoredProcedure;
            scriptCommand.CommandText = "ExecScript";
            scriptCommand.Parameters.Add("myScript", OleDbType.Char).Value = vfpScript;
            scriptCommand.ExecuteNonQuery();
        }
    
    您现在可以根据需要更改值,就像下面的用法一样

        DataTable dt = new DataTable(); // assuming this is already populated from your SQL Database.
        StringBuilder buildInsert = new StringBuilder();
        string connectionString = @"Provider=VFPOLEDB.1;Data Source=C:\test.dbf";
        OleDbConnection connection = new OleDbConnection(connectionString);
    
        using (OleDbCommand scriptCommand = connection.CreateCommand())
        {
             connection.Open();
    
             foreach(DataRow dr in dt.Rows)
             {
                 string id = dr["ID"].ToString();
                 string name = dr["Name"].ToString();
                 string details = dr["Details"].ToString();
                 string status = Convert.ToBoolean(dr["Status"]) ? ".t." : ".f.";
                 string createDate = "{^" + Convert.ToDateTime(dr["CreateDate"]).ToString("yyyy-MM-dd") + "}";
                 builderInsert.Append("INSERT INTO \"C:\test.dbf\" ([ID], [Name], [Details], [Status], [CreateDate]) VALUES (" + id + ",\"" + name + "\",\"" + details + "\"," + status + "," + createDate + ")" + Environment.NewLine);
    
                 scriptCommand.CommandType = CommandType.StoredProcedure;
                 scriptCommand.CommandText = "ExecScript";
                 scriptCommand.Parameters.Add("myScript", OleDbType.Char).Value = builderInsert;
                 scriptCommand.ExecuteNonQuery();
                 builderInsert = "";
              }
         }
    
    如果您有其他问题,请告诉我。 别忘了在你的机器上安装这个。

    要为您提供一个C#解决方案,我首先要下载适用于.DBF表的

    在C代码的顶部,添加

    using System.Data.SqlClient;
    using System.Data.OleDb;
    
    然后,在方法内移动数据

        void MoveFromSQLToDBF()
        {    
            // have a table to pull down your SQL Data...
            var dataFromSQL = new DataTable();
    
            // However your connection to your SQL-Server
            using (var sqlConn = new  SqlConnection("YourSQLConnectionString"))
            {
               using (var sqlCmd = new SqlCommand("", sqlConn))
               {
                  // Get all records from your table
                  sqlCmd.CommandText = "select * from CountryMaster";
                  sqlConn.Open();
                  var sqlDA = new SqlDataAdapter();
                  // populate into a temp C# table
                  sqlDA.Fill(dataFromSQL);
                  sqlConn.Close();
               }
            }
    
            // Now, create a connection to VFP 
            // connect to a PATH where you want the data.
            using (var vfpConn = new OleDbConnection(@"Provider=VFPOLEDB.1;Data Source=C:\SomePathOnYourMachine\"))
            {
               using (var vfpCmd = new OleDbCommand("", vfpConn))
               {
                  // Create table command for VFP
                  vfpCmd.CommandText = "CREATE TABLE testFromSQL ( ID Numeric(18,0), [Name] Char(100) NULL, [Details] Char(200) NULL, [Status] Logical NULL, [CreateDate] DATETIME NULL)";
    
                  vfpConn.Open();
                  vfpCmd.ExecuteNonQuery();
    
                  // Now, change the command to a SQL-Insert command, but PARAMETERIZE IT.
                  // "?" is a place-holder for the data
                  vfpCmd.CommandText = "insert into testFromSQL "
                     + "( ID, [Name], [Details], [Status], [CreateDate]) values ( ?, ?, ?, ?, ? )";
    
                  // Parameters added in order of the INSERT command above.. 
                  // SAMPLE values just to establish a basis of the column types
                  vfpCmd.Parameters.Add( new OleDbParameter( "parmID", 10000000 ));
                  vfpCmd.Parameters.Add( new OleDbParameter( "parmName", "sample string" ));
                  vfpCmd.Parameters.Add(new OleDbParameter( "parmDetails", "sample string" ));
                  vfpCmd.Parameters.Add(new OleDbParameter( "parmStatus", "sample string" ));
                  vfpCmd.Parameters.Add( new OleDbParameter( "parmCreateDate", DateTime.Now ));
    
                  // Now, for each row in the ORIGINAL SQL table, apply the insert to VFP
                  foreach (DataRow dr in dataFromSQL.Rows)
                  {
                     // set the parameters based on whatever current record is
                     vfpCmd.Parameters[0].Value = dr["ID"];
                     vfpCmd.Parameters[1].Value = dr["Name"];
                     vfpCmd.Parameters[2].Value = dr["Details"];
                     vfpCmd.Parameters[3].Value = dr["Status"];
                     vfpCmd.Parameters[4].Value = dr["CreateDate"];
                     // execute it
                     vfpCmd.ExecuteNonQuery();
                  }
    
                  // Finally, for compactness, use a VFP Script to copy to Excel (CSV) format
                  using (var vfpCmd2 = new OleDbCommand("", vfpConn))
                  {
                     vfpCmd2.CommandType = CommandType.StoredProcedure;
                     vfpCmd2.CommandText = "ExecScript";
    
                     vfpCmd2.Parameters.Add(new OleDbParameter( "csvScript", 
    @"Use testFromSQL
    copy to YourCompactFile.csv type csv
    use" ));
    
                     vfpCmd2.ExecuteNonQuery();
                  }
    
                  // close VFP connection
                  vfpConn.Close();
    
               }
            }
        }
    

    由于OleDb不支持复制类型CSV,我为您找到了

    我想这可能会回答您的问题,这是用于哪个RDBMS的?请添加一个标记,以指定您使用的是
    mysql
    postgresql
    sql server
    oracle
    还是
    db2
    -或其他完全不同的文件。因此,您希望将数据从sql server导出到dBase、Clipper或Foxpro文件(哪一个)?您根本不需要使用C#来实现这一点,您是否在SSMS中尝试过Integration Services或导出数据向导?该向导实际上创建了一个SSIS包,您可以根据需要对其进行编辑。如果需要,您甚至可以在C代码中使用相同的提供程序、连接字符串want@PanagiotisKanavos删除了使用工具时的答案。OP可以仿效@marc_s的例子,他的笔记上写着:dbf文件大小必须非常紧凑。我在第一种方法中遇到了错误“命名空间'IRI.Ket'中不存在类型或命名空间名称'IO'(是否缺少程序集引用?)“@Chirag I更新GitHub源代码。如果您有任何其他问题,请告诉我。我不会投反对票,但如果未知程序员使用随机GitHub库出现类似错误,我肯定会犹豫。是的。我已经将其更改为200并解决了错误,但文件大小为54MB(太大)。如果我想把它降到小于10 MB,你会怎么说?不管怎样,如果你正在寻找一个可以减少DBF文件大小的答案(尽管在技术上它对给定的数据集没有意义),考虑编辑你的问题并提一下你的问题。不管怎样,我建议您寻找其他格式,不要使用.dbf格式。投票否决我的人:我提供的信息与OP提供的信息一样多。OP甚至没有展示他们尝试过的任何作品。对于填鸭式喂食的请求,最好的回答方向是让请求者能够更多地思考、沟通和参与。我没有反对投票,但正如你看到的,答案是经过编辑的,似乎他在寻找一个完全不同的问题,因此如果你能帮助并相信他想要什么,你可能需要编辑你的答案(使用给定的数据集压缩dbf文件!)可以完成。@Chirag,我还添加了将结果导出为CSV文件的功能,该功能会自动修剪数据并包含列标题。虽然使用VFP OleDB的目的很好,但也存在问题(包括SQL注入)。连接字符串应始终指向路径,而不是显式表。因此,当您发出“创建表”或“插入到”命令时,您只需指定表名,它将应用于指定路径中的表。您可能没有读取/写入/修改权限,尤其是在根C:\级别,与示例不同。它可以工作,but需要调整,还需要从SQL Server中提取一个对象,然后插入到VFP ta中
        void MoveFromSQLToDBF()
        {    
            // have a table to pull down your SQL Data...
            var dataFromSQL = new DataTable();
    
            // However your connection to your SQL-Server
            using (var sqlConn = new  SqlConnection("YourSQLConnectionString"))
            {
               using (var sqlCmd = new SqlCommand("", sqlConn))
               {
                  // Get all records from your table
                  sqlCmd.CommandText = "select * from CountryMaster";
                  sqlConn.Open();
                  var sqlDA = new SqlDataAdapter();
                  // populate into a temp C# table
                  sqlDA.Fill(dataFromSQL);
                  sqlConn.Close();
               }
            }
    
            // Now, create a connection to VFP 
            // connect to a PATH where you want the data.
            using (var vfpConn = new OleDbConnection(@"Provider=VFPOLEDB.1;Data Source=C:\SomePathOnYourMachine\"))
            {
               using (var vfpCmd = new OleDbCommand("", vfpConn))
               {
                  // Create table command for VFP
                  vfpCmd.CommandText = "CREATE TABLE testFromSQL ( ID Numeric(18,0), [Name] Char(100) NULL, [Details] Char(200) NULL, [Status] Logical NULL, [CreateDate] DATETIME NULL)";
    
                  vfpConn.Open();
                  vfpCmd.ExecuteNonQuery();
    
                  // Now, change the command to a SQL-Insert command, but PARAMETERIZE IT.
                  // "?" is a place-holder for the data
                  vfpCmd.CommandText = "insert into testFromSQL "
                     + "( ID, [Name], [Details], [Status], [CreateDate]) values ( ?, ?, ?, ?, ? )";
    
                  // Parameters added in order of the INSERT command above.. 
                  // SAMPLE values just to establish a basis of the column types
                  vfpCmd.Parameters.Add( new OleDbParameter( "parmID", 10000000 ));
                  vfpCmd.Parameters.Add( new OleDbParameter( "parmName", "sample string" ));
                  vfpCmd.Parameters.Add(new OleDbParameter( "parmDetails", "sample string" ));
                  vfpCmd.Parameters.Add(new OleDbParameter( "parmStatus", "sample string" ));
                  vfpCmd.Parameters.Add( new OleDbParameter( "parmCreateDate", DateTime.Now ));
    
                  // Now, for each row in the ORIGINAL SQL table, apply the insert to VFP
                  foreach (DataRow dr in dataFromSQL.Rows)
                  {
                     // set the parameters based on whatever current record is
                     vfpCmd.Parameters[0].Value = dr["ID"];
                     vfpCmd.Parameters[1].Value = dr["Name"];
                     vfpCmd.Parameters[2].Value = dr["Details"];
                     vfpCmd.Parameters[3].Value = dr["Status"];
                     vfpCmd.Parameters[4].Value = dr["CreateDate"];
                     // execute it
                     vfpCmd.ExecuteNonQuery();
                  }
    
                  // Finally, for compactness, use a VFP Script to copy to Excel (CSV) format
                  using (var vfpCmd2 = new OleDbCommand("", vfpConn))
                  {
                     vfpCmd2.CommandType = CommandType.StoredProcedure;
                     vfpCmd2.CommandText = "ExecScript";
    
                     vfpCmd2.Parameters.Add(new OleDbParameter( "csvScript", 
    @"Use testFromSQL
    copy to YourCompactFile.csv type csv
    use" ));
    
                     vfpCmd2.ExecuteNonQuery();
                  }
    
                  // close VFP connection
                  vfpConn.Close();
    
               }
            }
        }