1

メモリ内のデータテーブル(vb.net)とその列(スキーマ)をSQLサーバーの新規または既存のテーブルにコピーする方法はありますか?また、一時テーブルに列が追加されている場合、既存のSQLサーバーテーブルに新しい列を追加してデータを一括コピーする方法はありますか?

4

3 に答える 3

2

DataTableをSQLServerに永続化するために使用するものは次のとおりです。これは、C#で記述されていますが、かなり簡単に変換できるはずです。

public static string CreateCopyTableDataSQLServer(DataTable dt, string tableName, string connectionString)
{
    //Create the Destination Table based upon the structure of the DataTable
    string sql = string.Empty;
    string retValue = string.Empty;
    StringBuilder sbu;

    try
    {
        if (dt.Rows.Count == 0)
        {
            retValue += "The table " + tableName + " was NOT created because the source table contained zero (0) rows of data";
        }
        else
        {
            sbu = new StringBuilder(string.Format("IF  EXISTS (SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'[dbo].[{0}]') AND type in (N'U')) DROP TABLE [dbo].[{0}] ", tableName));
            sbu.Append("Create Table " + tableName + " (");

            string dataType = string.Empty;

            foreach (DataColumn column in dt.Columns)
            {
                switch (column.DataType.Name)
                {
                    case "String":
                        dataType = " nvarchar(MAX) ";
                        break;
                    case "DateTime":
                        dataType = " nvarchar(MAX) ";
                        break;
                    case "Boolean":
                        dataType = " nvarchar(MAX) ";
                        break;
                    case "Int32":
                        dataType = " int ";
                        break;
                    case "Byte[]":
                        dataType = " varbinary(8000) ";
                        break;
                    default:
                        dataType = " nvarchar(MAX) ";
                        break;
                }
                string columnName = column.ColumnName.ToString();
                columnName = columnName.FormatProperNameCase();
                columnName = column.ColumnName.ToString().Replace(" ", "_").Replace("-", "_").Replace("#", "_").FormatRemoveNonLettersNumbers();
                sbu.Append("[" + columnName + "]" + dataType + " null, ");
            }

            sbu.Remove(sbu.Length - 2, 2);
            sbu.Append(")");
            sql = sbu.ToString();
            sql = sql.Replace("/", "_").Replace("\\", "_");

            //Copy the Data From the Data Table into the destination Table that was created above
            bool errorRetValue = SQLServerBulkCopy(dt, sql, tableName, connectionString);

            if (!errorRetValue)
            {
                retValue += " \r\n";
                retValue += "There was an error!";
            }
        }
        return retValue;
    }
    catch (Exception ex)
    {
        retValue = string.Format("Error - There was a problem with table {0} and thus it's data has NOT been transferred - {1}", tableName, ex.Message);
        return retValue;
    }
}

public static bool SQLServerBulkCopy(DataTable dt, string Sql, string TableName, string connectionString, bool connectionTypeSQL = true)
{
    try
    {
        if (connectionTypeSQL)
        {
            using (SqlConnection conn = new SqlConnection(connectionString))
            {
                conn.Open();
                using (SqlBulkCopy sqlcpy = new SqlBulkCopy(conn))
                {
                    using (SqlCommand cmd = new SqlCommand(Sql, conn))
                    {
                        cmd.ExecuteNonQuery();
                        sqlcpy.DestinationTableName = TableName;  //copy the datatable to the sql table
                        sqlcpy.WriteToServer(dt);
                    }
                }
            }
            return true;
        }
        else
        {
            throw new ArgumentOutOfRangeException("This method is only for SQL Server Engines");
        }
    }
    catch (Exception ex)
    {
        return false;
    }
}
于 2012-12-18T19:29:47.720 に答える
1

新しいテーブルを作成するには:

select  *
into    YourDb.dbo.NewTable
from    #YourTempTable

既存のテーブルに追加するには:

insert  YourDb.dbo.ExistingTable
select  *
from    #YourTempTable
于 2012-12-18T19:03:05.990 に答える
0

私が働いている場所では、リンクサーバーは許可されないため、VB.NETを使用して2つのテーブルを異なるサーバーから転送しました。

  1. ソースSQLテーブルをDatatableにコピーする
  2. Datatableの列のマッピング
  3. データテーブルを宛先のSQLテーブルにコピーする

コードは以下のとおりです。

Sub BulkTransferSQLTables(strSchema As String, strTable As String, StrOutputServer As String, StrOutputDatabase As String) ', strEndSrvrDb As String)
    Dim DTBulkTransfer As New DataTable
    'get table of information
    Dim strSchemaTable As String = strSchema & "." & strTable
    Dim sqlstring As String = "Select * from " & strSchemaTable
    Dim Conn As SqlConnection = New SqlConnection("Data Source=" & PubstrServer & ";Initial Catalog=" & PubstrDatabase & ";Integrated Security=True") 'connection to server end
    Dim selectCMD As SqlCommand
    Dim adapter As SqlDataAdapter
    adapter = New SqlDataAdapter(sqlstring, Conn)


    'fill dataset
    Conn.Open()
    adapter.Fill(DTBulkTransfer)

    'Debug.Print(DTBulkTransfer.Rows.Count & " Rows, " & DTBulkTransfer.Columns.Count & " Cols ") 'works


    'build create table statement using details of destination table
    Dim strColname As String
    Dim intRecCount As Integer
    'Dim strSchema As String = "SuffolkPseudo"
    'Dim strTable As String = "Acute_Supporting"
    strSchemaTable = strSchema & "." & strTable
    Dim strCreateTableSQL As String = "CREATE TABLE [" & StrOutputDatabase & "].[" & strSchema & "].[" & strTable & "]("

    Dim strSQL As String = " select [Statement], [RowNo] = ROW_NUMBER() OVER (ORDER BY Statement) FROM [" & PubstrDatabase & "].[dbo].[vwTableAndColumns] " & _
        "where [TABLE_SCHEMA] = '" & strSchema & "' and table_name = '" & strTable & "'"

    Dim strSQL2 As String = "" & _
    " with CTE as ( " & _
    " " & _
    strSQL & _
    " ) " & _
    " " & _
    " select count(*) from CTE "

    intRecCount = GetSQLTableVal(strSQL2)

    For X = 1 To intRecCount
        strSQL2 = "" & _
                " with CTE as ( " & _
                " " & _
                strSQL & _
                " ) " & _
                " " & _
                " select * from CTE "
        strColname = GetSQLTableVal(strSQL2 & " Where [RowNo] = " & X)

        strCreateTableSQL = strCreateTableSQL & " " & Chr(13) & strColname
    Next

    strCreateTableSQL = Microsoft.VisualBasic.Left(strCreateTableSQL, Microsoft.VisualBasic.Len(strCreateTableSQL) - 1) & ") ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]"

    Debug.Print(strCreateTableSQL)


    Conn.Close()

    Dim Conn2 As SqlConnection = New SqlConnection("Data Source=" & StrOutputServer & ";Initial Catalog=" & StrOutputDatabase & ";Integrated Security=True") 'connection to server end


    'create sql string to check if table exists or not.

    strSQL = " select count(*) FROM [" & StrOutputDatabase & "].sys.Tables as t1 " & _
            " inner join [" & StrOutputDatabase & "].sys.schemas as t2 " & _
            " ON t1.schema_id = t2.schema_id" & _
            " where t2.name = '" & strSchema & "' " & _
            " and t1.name = '" & strTable & "'"


    If GetSQLTableValExternalServer(strSQL, StrOutputServer, StrOutputDatabase) > 0 Then

        Conn2.Open()
        'drop old table in destination area and recreate table.
        strSQL = "drop table " & StrOutputDatabase & "." & strSchema & "." & strTable
        selectCMD = New SqlCommand(strSQL, Conn2)
        selectCMD.CommandTimeout = 600
        selectCMD.ExecuteNonQuery()
        Conn2.Close()
    End If

    Conn2.Open()
    'create the table structure 
    selectCMD = New SqlCommand(strCreateTableSQL, Conn2)
    selectCMD.CommandTimeout = 600

    selectCMD.ExecuteNonQuery()


    'list datatable columns 

    Dim name(DTBulkTransfer.Columns.Count) As String
    Dim i As Integer = 0

    'transfer to sql database from datatable to newly created empty detsination table
    Using bulkcopy As SqlBulkCopy = New SqlBulkCopy(Conn2)

        bulkcopy.BulkCopyTimeout = 3000
        bulkcopy.DestinationTableName = strSchemaTable


        For Each column As DataColumn In DTBulkTransfer.Columns
            name(i) = column.ColumnName
            Dim ColMap As New SqlBulkCopyColumnMapping(name(i).ToString, name(i).ToString)
            bulkcopy.ColumnMappings.Add(ColMap)
            Debug.Print("dt COLUMN: " & name(i).ToString)
            i += 1
        Next


        bulkcopy.WriteToServer(DTBulkTransfer)
    End Using

    Conn2.Close()

    MsgBox("Bulk Transfer Complete")


End Sub

ありがとう

Eddy Jawed

于 2014-09-04T11:02:38.240 に答える