1

I am trying to write a program which creates a .csv file from an Access table. I'm not sure how to do this and everything I've found while researching this is how to do the opposite, creating an Access table from a .csv file.

So far, I have created a windows forms application that allows the user to select a data path to the access directory (.mdb) and then after pushing the "Go" button, a list of the tables in the directory is shown in a listbox.

What I need to do next, which I have no idea how to, is allow the user to select one of the tables, which would then create a .csv file from the selected table. Here is my code so far:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Data.OleDb;
using System.Data.Common;

namespace TranslatorHelper
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
    private void btnPath_Click(object sender, EventArgs e)
    {
        string dialogText = "";
        // Show the dialog and get result.
        DialogResult result = openFileDialog1.ShowDialog();
        if (result == DialogResult.OK) // Test result.
        {
            dialogText = openFileDialog1.ToString();
            dialogText = dialogText.Replace("System.Windows.Forms.OpenFileDialog: Title: , FileName: ", "");
            txtDataPath.Text = dialogText;
        }
    }

    private void btnGetTables_Click(object sender, EventArgs e)
    {
        // Microsoft Access provider factory
        DbProviderFactory factory =
        DbProviderFactories.GetFactory("System.Data.OleDb");

        DataTable userTables = null;

        using (DbConnection connection = factory.CreateConnection())
        {
            connection.ConnectionString = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source="+txtDataPath.Text;

            // We only want user tables, not system tables
            string[] restrictions = new string[4];
            restrictions[3] = "Table";

            connection.Open();

            // Get list of user tables
            userTables = connection.GetSchema("Tables", restrictions);
        }

    // Add list of table names to listBox
    for (int i = 0; i < userTables.Rows.Count; i++)
    lstTables.Items.Add(userTables.Rows[i][2].ToString());

    }

    private void lstTables_SelectedIndexChanged(object sender, EventArgs e)
    {

    }

Please offer any advice you can, anything is appreciated, I'm really stuck here.

4

1 回答 1

3

也许我可以将您推向正确的方向:

您有一个开始,即 DbConnection。然后,您可以从中创建一个 DbCommand:

DbCommand command = connection.CreateCommand();

从那里,您可以分配文本,例如:

command.CommandText = "SELECT * FROM " + tableName;  //you might have to wrap the table name with quotes or square brackets!

然后你可以得到一个读者:

DbDataReader reader = command.ExecuteReader(CommandBehavior.Default);

一旦你有了阅读器,你就得到了数据,这意味着你可以:

DataTable dt = new DataTable("MyNewTable");
dt.Load(reader);
foreach (DataRow row in dt.Rows)
{
    foreach (DataColumn dc in row.Columns)
    {
        if (!String.IsNullOrEmpty(sb.ToString()))
            sb.Append(",");
        sb.Append(row[dc.ColumnName].ToString());
    }
    sb.Append("\n");
}

要获得 ListBox 选择,您可以使用:

lstTables.SelectedItem.ToString()

那应该给你项目,或者在你的情况下是一个表名。不要忘记某些词在 SQL 中是保留的(这也取决于它是哪个 SQL),因此您可能必须小心在 CommandText 参数的 SQL 字符串中直接使用表名。

此外,我认为不需要使用 SelectedIndexChanged 事件处理程序,除非您需要在用户做出选择后立即执行某些操作。如果您希望用户的行为是做出选择然后单击按钮启动进程,则无需处理更改。

于 2013-05-23T19:42:40.313 回答