将MS Excel数据粘贴到SQL Server
我在Excel中有一堆行,我想粘贴到MS SQL中的新表。 有一个简单的方法吗?
过去我成功地使用了这种技术:
使用Excel为SQL Server生成插入
(…)跳过一列(或用它来做笔记),然后在其中input如下的公式:
="insert into tblyourtablename (yourkeyID_pk, intmine, strval) values ("&A4&", "&B4&", N'"&C4&"')"
现在,您已经获得了包含主键(PK),整数和Unicodestring的表的插入语句。 (……)
如果您拥有SQL Server Management Studio,则可以使用鼠标将其从Excel中复制并粘贴到Management Studio中的表中。 只是
- 转到您要粘贴的表格。
- select“编辑排名前200的行”。
- 右键单击任意位置并select粘贴。
在执行此操作之前,您必须匹配Excel和Management Studio之间的列。 另外,您必须使用Management Studio中的表devise器放置任何不可编辑列(最右边)。
整个过程需要几秒钟( 设置和启动 – 不一定执行),并且不需要任何SQL语句。
为了将来的参考:
您可以通过这样做将数据从excel表格复制粘贴到SQL表格中:
在Excel中select数据并按下Ctrl + C
- 在Excel中select数据并按下Ctrl + C
- 在SQL Server Management Studio中,右键单击该表,然后select“ 编辑排名前200的行”
- 滚动到底部并通过单击行标题来select整个空行
- 通过按Ctrl + V粘贴数据
注意:通常,表格的第一列是带有自动生成/增加的ID的ID列。 当您粘贴数据时,它将开始将Excel中最左侧的选定列插入到SSMS中最左侧的列中,从而将数据插入到ID列中。 为了避免在select的最左边部分保留一个空列,以便跳过SSMS中的那一列。 这将导致SSMS插入默认数据,即自动生成的ID。 此外,您可以跳过其他列,方法是在Excel工作表select的相同序号位置处将空列标记为要跳过的列。 这将使SSMS插入默认值(或NULL ,如果没有指定默认值)。
最简单的方法是在XLS中创build一个计算列,它将生成插入语句的语法。 然后将这些插入复制到一个文本文件中,然后在SQL上执行。 其他的select是购买Excel的数据库连接附件,并写VBA代码来实现。
我想一些数据库可以从CSV(逗号分隔值)文件导入数据,你可以从EXEL导出。 或者至less使用csvparsing器很容易(find一个适合您的语言,不要自己创build一个 – 比看起来更难)将其导入数据库。
我对MS SQL不熟悉,但是如果它直接支持,我不会感到惊讶。
无论如何,我认为必须要求Exel表单和数据库表中的结构是相似的。
如果接口的工作方式是最后一次使用的方式,那么您可以在Excel中select区域,复制它,打开SQL Server并将数据粘贴到表格中,就像使用Access一样。
或者你可以在Excel和SQL Server之间build立一个ODBC链接。
我开发了一个Excel VBAmacros,用于将任何select从Excel中剪切并粘贴到SQL Server中,创build一个新表。 macros是伟大的快速和肮脏的表创作高达几千行和多列(理论上可以pipe理多达200列)。 macros尝试自动检测标题名称,并为每列(最多可处理1000个字符的varchar列)分配最合适的数据types。
推荐的安装程序:
- 确保Excel已启用运行macros。 (文件 – >选项 – >信任中心 – >信任中心设置 – >macros设置 – >启用所有macros..)
- 将下面的VBA代码复制到与您的个人工作簿关联的模块(以便macros可用于所有工作表)
- 为macros指定适当的按键(我已经分配了Ctrl Shift X)
- 保存您的个人工作簿
使用macros
- selectExcel中的单元格(包括列标题,如果存在的话)以传输到SQL
- 按分配的关键字组合来运行macros
- 按照提示进行操作。 (默认表名是##表)
- 将剪贴板内容粘贴到SSMS窗口并运行生成的SQL代码。 BriFri 238
VBA代码:
Sub TransferToSQL() ' ' TransferToSQL Macro ' This macro prepares data for pasting into SQL Server and posts it to the clipboard for inserting into SSMS ' It attempts to automatically detect header rows and does a basic analysis of the first 15 rows to determine the most appropriate datatype to use handling text entries upto 1000 chars. ' ' Max Number of Columns: 200 ' ' Keyboard Shortcut: Ctrl+Shift+X ' ' ver Date Reason ' === ==== ====== ' 1.6 06/2012 Fixed bug that prevented auto exit if no selection made / auto exit if blank Tablename entered or 'cancel' button pressed ' 1.5 02/2012 made use of function fn_ColLetter to retrieve the Column Letter for a specified column ' 1.4 02/2012 Replaces any Tabs in text data to spaces to prevent Double quotes being output in final results ' 1.3 02/2012 Place the 'drop table if already exists' code into a separate batch to prevent errors when inserting new table with same name but different shape and > 100 rows ' 1.2 01/2012 If null dates encountered code to cast it as Null rather than '00-Jan-1900' ' 1.1 10/2011 Code to drop the table if already exists ' 1.0 03/2011 Created Dim intLastRow As Long Dim intlastColumn As Integer Dim intRow As Long Dim intDataStartRow As Long Dim intColumn As Integer Dim strKeyWord As String Dim intPos As Integer Dim strDataTypeLevel(4) As String Dim strColumnHeader(200) As String Dim strDataType(200) As String Dim intRowCheck As Integer Dim strFormula(20) As String Dim intHasHeaderRow As Integer Dim strCellRef As String Dim intFormulaCount As Integer Dim strSQLTableName As String Dim strSQLTableName_Encap As String Dim intdataTypelevel As Integer Const strConstHeaderKeyword As String = "ID,URN,name,Title,Job,Company,Contact,Address,Post,Town,Email,Tele,phone,Area,Region,Business,Total,Month,Week,Year," Const intConstMaxBatchSize As Integer = 100 Const intConstNumberRowsToAnalyse As Integer = 100 intHasHeaderRow = 0 strDataTypeLevel(1) = "VARCHAR(1000)" strDataTypeLevel(2) = "FLOAT" strDataTypeLevel(3) = "INTEGER" strDataTypeLevel(4) = "DATETIME" ' Use current selection and paste to new temp worksheet Selection.Copy Workbooks.Add ' add temp 'Working' Workbook ' Paste "Values Only" back into new temp workbook Range("A3").Select ' Goto 3rd Row Selection.PasteSpecial Paste:=xlFormats, Operation:=xlNone, SkipBlanks:=False, Transpose:=False ' Copy Format of Selection Selection.PasteSpecial Paste:=xlValues, Operation:=xlNone, SkipBlanks:=False, Transpose:=False ' Copy Values of Selection ActiveCell.SpecialCells(xlLastCell).Select ' Goto last cell intLastRow = ActiveCell.Row intlastColumn = ActiveCell.Column ' Check to make sure that there are cells which are selected If intLastRow = 3 And intlastColumn = 1 Then Application.DisplayAlerts = False ' Temporarily switch off Display Alerts ActiveWindow.Close ' Delete newly created worksheet Application.DisplayAlerts = True ' Switch display alerts back on MsgBox "*** Please Make selection before running macro - Terminating ***", vbOKOnly, "Transfer Data to SQL Server" Exit Sub End If ' Prompt user for Name of SQL Server table strSQLTableName = InputBox("SQL Server Table Name?", "Transfer Excel Data To SQL", "##Table") ' if blank table name entered or 'Cancel' selected then exit If strSQLTableName = "" Then Application.DisplayAlerts = False ' Temporarily switch off Display Alerts ActiveWindow.Close ' Delete newly created worksheet Application.DisplayAlerts = True ' Switch display alerts back on Exit Sub End If ' encapsulate tablename with square brackets if user has not already done so strSQLTableName_Encap = Replace(Replace(Replace("[" & Replace(strSQLTableName, ".", "].[") & "]", "[]", ""), "[[", "["), "]]", "]") ' Try to determine if the First Row is a header row or contains data and if a header load names of Columns Range("A3").Select For intColumn = 1 To intlastColumn ' first check to see if the first row contains any pure numbers or pure dates If IsNumeric(ActiveCell.Value) Or IsDate(ActiveCell.Value) Then intHasHeaderRow = vbNo intDataStartRow = 3 Exit For Else strColumnHeader(intColumn) = ActiveCell.Value ActiveCell.Offset(1, 0).Range("A1").Select ' go to the row below If IsNumeric(ActiveCell.Value) Or IsDate(ActiveCell.Value) Then intHasHeaderRow = vbYes intDataStartRow = 4 End If ActiveCell.Offset(-1, 0).Range("A1").Select ' go back up to the first row If intHasHeaderRow = 0 Then ' if still not determined if header exists: Look for header using keywords intPos = 1 While intPos < Len(strConstHeaderKeyword) And intHasHeaderRow = 0 strKeyWord = Mid$(strConstHeaderKeyword, intPos, InStr(intPos, strConstHeaderKeyword, ",") - intPos) If InStr(1, ActiveCell.Value, strKeyWord) > 0 Then intHasHeaderRow = vbYes intDataStartRow = 4 End If intPos = InStr(intPos, strConstHeaderKeyword, ",") + 1 Wend End If End If ActiveCell.Offset(0, 1).Range("A1").Select ' Goto next column Next intColumn ' If auto header row detection has failed ask the user to manually select If intHasHeaderRow = 0 Then intHasHeaderRow = MsgBox("Does current selection have a header row?", vbYesNo, "Auto header row detection failure") If intHasHeaderRow = vbYes Then intDataStartRow = 4 Else intDataStartRow = 3 End If End If ' *** Determine the Data Type of each Column *** ' Go thru each Column to find Data types If intLastRow < intConstNumberRowsToAnalyse Then ' Check the first intConstNumberRowsToAnalyse rows or to end of selection whichever is less intRowCheck = intLastRow Else intRowCheck = intConstNumberRowsToAnalyse End If For intColumn = 1 To intlastColumn intdataTypelevel = 5 For intRow = intDataStartRow To intRowCheck Application.Goto Reference:="R" & CStr(intRow) & "C" & CStr(intColumn) If ActiveCell.Value = "" Then ' ignore blank (null) values ElseIf IsDate(ActiveCell.Value) = True And Len(ActiveCell.Value) >= 8 Then If intdataTypelevel > 4 Then intdataTypelevel = 4 ElseIf IsNumeric(ActiveCell.Value) = True And InStr(1, CStr(ActiveCell.Value), ".") = 0 And (Left(CStr(ActiveCell.Value), 1) <> "0" Or ActiveCell.Value = "0") And Len(ActiveCell.Value) < 10 Then If intdataTypelevel > 3 Then intdataTypelevel = 3 ElseIf IsNumeric(ActiveCell.Value) = True And InStr(1, CStr(ActiveCell.Value), ".") >= 1 Then If intdataTypelevel > 2 Then intdataTypelevel = 2 Else intdataTypelevel = 1 Exit For End If Next intRow If intdataTypelevel = 5 Then intdataTypelevel = 1 strDataType(intColumn) = strDataTypeLevel(intdataTypelevel) Next intColumn ' *** Build up the SQL intFormulaCount = 1 If intHasHeaderRow = vbYes Then ' *** Header Row *** Application.Goto Reference:="R4" & "C" & CStr(intlastColumn + 1) ' Goto next column in first data row of selection strFormula(intFormulaCount) = "= ""SELECT " For intColumn = 1 To intlastColumn If strDataType(intColumn) = "DATETIME" Then ' Code to take Excel Dates back to text strCellRef = "Text(" & fn_ColLetter(intColumn) & "4,""dd-mmm-yyyy hh:mm:ss"")" ElseIf strDataType(intColumn) = "VARCHAR(1000)" Then strCellRef = "SUBSTITUTE(" & fn_ColLetter(intColumn) & "4,""'"",""''"")" ' Convert any single ' to double '' Else strCellRef = fn_ColLetter(intColumn) & "4" End If strFormula(intFormulaCount) = strFormula(intFormulaCount) & "CAST('""& " & strCellRef & " & ""' AS " & strDataType(intColumn) & ") AS [" & strColumnHeader(intColumn) & "]" If intColumn < intlastColumn Then strFormula(intFormulaCount) = strFormula(intFormulaCount) + ", " Else strFormula(intFormulaCount) = strFormula(intFormulaCount) + " UNION ALL """ End If ' since each cell can only hold a maximum no. of chars if Formula string gets too big continue formula in adjacent cell If Len(strFormula(intFormulaCount)) > 700 And intColumn < intlastColumn Then strFormula(intFormulaCount) = strFormula(intFormulaCount) + """" intFormulaCount = intFormulaCount + 1 strFormula(intFormulaCount) = "= """ End If Next intColumn ' Assign the formula to the cell(s) just right of the selection For intColumn = 1 To intFormulaCount ActiveCell.Value = strFormula(intColumn) If intColumn < intFormulaCount Then ActiveCell.Offset(0, 1).Range("A1").Select ' Goto next column Next intColumn ' Auto Fill the formula for the full length of the selection ActiveCell.Offset(0, -intFormulaCount + 1).Range("A1:" & fn_ColLetter(intFormulaCount) & "1").Select If intLastRow > 4 Then Selection.AutoFill Destination:=Range(fn_ColLetter(intlastColumn + 1) & "4:" & fn_ColLetter(intlastColumn + intFormulaCount) & CStr(intLastRow)), Type:=xlFillDefault ' Go to start row of data selection to add 'Select into' code ActiveCell.Value = "SELECT * INTO " & strSQLTableName_Encap & " FROM (" & ActiveCell.Value ' Go to cells above data to insert code for deleting old table with the same name in separate SQL batch ActiveCell.Offset(-1, 0).Range("A1").Select ' go to the row above ActiveCell.Value = "GO" ActiveCell.Offset(-1, 0).Range("A1").Select ' go to the row above If Left(strSQLTableName, 1) = "#" Then ' temp table ActiveCell.Value = "IF OBJECT_ID('tempdb.." & strSQLTableName & "') IS NOT NULL DROP TABLE " & strSQLTableName_Encap Else ActiveCell.Value = "IF OBJECT_ID('" & strSQLTableName & "') IS NOT NULL DROP TABLE " & strSQLTableName_Encap End If ' For Big selections (ie several 100 or 1000 rows) SQL Server takes a very long time to do a multiple union - Split up the table creation into many inserts intRow = intConstMaxBatchSize + 4 ' add 4 to make sure 1st batch = Max Batch Size While intRow < intLastRow Application.Goto Reference:="R" & CStr(intRow - 1) & "C" & CStr(intlastColumn + intFormulaCount) ' Goto Row before intRow and the last column in formula selection ActiveCell.Value = Replace(ActiveCell.Value, " UNION ALL ", " ) a") ' Remove last 'UNION ALL' Application.Goto Reference:="R" & CStr(intRow) & "C" & CStr(intlastColumn + 1) ' Goto intRow and the first column in formula selection ActiveCell.Value = "INSERT " & strSQLTableName_Encap & " SELECT * FROM (" & ActiveCell.Value intRow = intRow + intConstMaxBatchSize ' increment intRow by intConstMaxBatchSize Wend ' Delete the last 'UNION AlL' replacing it with brackets to mark the end of the last insert Application.Goto Reference:="R" & CStr(intLastRow) & "C" & CStr(intlastColumn + intFormulaCount) ActiveCell.Value = Replace(ActiveCell.Value, " UNION ALL ", " ) a") ' Select all the formula cells ActiveCell.Offset(-intLastRow + 2, 1 - intFormulaCount).Range("A1:" & fn_ColLetter(intFormulaCount + 1) & CStr(intLastRow - 1)).Select Else ' *** No Header Row *** Application.Goto Reference:="R3" & "C" & CStr(intlastColumn + 1) ' Goto next column in first data row of selection strFormula(intFormulaCount) = "= ""SELECT " For intColumn = 1 To intlastColumn If strDataType(intColumn) = "DATETIME" Then strCellRef = "Text(" & fn_ColLetter(intColumn) & "3,""dd-mmm-yyyy hh:mm:ss"")" ' Format Excel dates into a text Date format that SQL will pick up ElseIf strDataType(intColumn) = "VARCHAR(1000)" Then strCellRef = "SUBSTITUTE(" & fn_ColLetter(intColumn) & "3,""'"",""''"")" ' Change all single ' to double '' Else strCellRef = fn_ColLetter(intColumn) & "3" End If ' Since no column headers: Name each column "Column001",Column002".. strFormula(intFormulaCount) = strFormula(intFormulaCount) & "CAST('""& " & strCellRef & " & ""' AS " & strDataType(intColumn) & ") AS [Column" & CStr(intColumn) & "]" If intColumn < intlastColumn Then strFormula(intFormulaCount) = strFormula(intFormulaCount) + ", " Else strFormula(intFormulaCount) = strFormula(intFormulaCount) + " UNION ALL """ End If ' since each cell can only hold a maximum no. of chars if Formula string gets too big continue formula in adjacent cell If Len(strFormula(intFormulaCount)) > 700 And intColumn < intlastColumn Then strFormula(intFormulaCount) = strFormula(intFormulaCount) + """" intFormulaCount = intFormulaCount + 1 strFormula(intFormulaCount) = "= """ End If Next intColumn ' Assign the formula to the cell(s) just right of the selection For intColumn = 1 To intFormulaCount ActiveCell.Value = strFormula(intColumn) If intColumn < intFormulaCount Then ActiveCell.Offset(0, 1).Range("A1").Select ' Goto next column Next intColumn ' Auto Fill the formula for the full length of the selection ActiveCell.Offset(0, -intFormulaCount + 1).Range("A1:" & fn_ColLetter(intFormulaCount) & "1").Select If intLastRow > 4 Then Selection.AutoFill Destination:=Range(fn_ColLetter(intlastColumn + 1) & "3:" & fn_ColLetter(intlastColumn + intFormulaCount) & CStr(intLastRow)), Type:=xlFillDefault ' Go to start row of data selection to add 'Select into' code ActiveCell.Value = "SELECT * INTO " & strSQLTableName_Encap & " FROM (" & ActiveCell.Value ' Go to cells above data to insert code for deleting old table with the same name in separate SQL batch ActiveCell.Offset(-1, 0).Range("A1").Select ' go to the row above ActiveCell.Value = "GO" ActiveCell.Offset(-1, 0).Range("A1").Select ' go to the row above If Left(strSQLTableName, 1) = "#" Then ' temp table ActiveCell.Value = "IF OBJECT_ID('tempdb.." & strSQLTableName & "') IS NOT NULL DROP TABLE " & strSQLTableName_Encap Else ActiveCell.Value = "IF OBJECT_ID('" & strSQLTableName & "') IS NOT NULL DROP TABLE " & strSQLTableName_Encap End If ' For Big selections (ie serveral 100 or 1000 rows) SQL Server takes a very long time to do a multiple union - Split up the table creation into many inserts intRow = intConstMaxBatchSize + 3 ' add 3 to make sure 1st batch = Max Batch Size While intRow < intLastRow Application.Goto Reference:="R" & CStr(intRow - 1) & "C" & CStr(intlastColumn + intFormulaCount) ' Goto Row before intRow and the last column in formula selection ActiveCell.Value = Replace(ActiveCell.Value, " UNION ALL ", " ) a") ' Remove last 'UNION ALL' Application.Goto Reference:="R" & CStr(intRow) & "C" & CStr(intlastColumn + 1) ' Goto intRow and the first column in formula selection ActiveCell.Value = "INSERT " & strSQLTableName_Encap & " SELECT * FROM (" & ActiveCell.Value intRow = intRow + intConstMaxBatchSize ' increment intRow by intConstMaxBatchSize Wend ' Delete the last 'UNION AlL' Application.Goto Reference:="R" & CStr(intLastRow) & "C" & CStr(intlastColumn + intFormulaCount) ActiveCell.Value = Replace(ActiveCell.Value, " UNION ALL ", " ) a") ' Select all the formula cells ActiveCell.Offset(-intLastRow + 1, 1 - intFormulaCount).Range("A1:" & fn_ColLetter(intFormulaCount + 1) & CStr(intLastRow)).Select End If ' Final Selection to clipboard and Cleaning of data Selection.Copy Selection.PasteSpecial Paste:=xlValues, Operation:=xlNone, SkipBlanks:=False, Transpose:=False ' Repaste "Values Only" back into cells Selection.Replace What:="CAST('' AS", Replacement:="CAST(NULL AS", LookAt:=xlPart, SearchOrder:=xlByRows, MatchCase:=False ' convert all blank cells to NULL Selection.Replace What:="'00-Jan-1900 00:00:00'", Replacement:="NULL", LookAt:=xlPart, SearchOrder:=xlByRows, MatchCase:=False ' convert all blank Date cells to NULL Selection.Replace What:="'NULL'", Replacement:="NULL", LookAt:=xlPart, SearchOrder:=xlByRows, MatchCase:=False ' convert all 'NULL' cells to NULL Selection.Replace What:=vbTab, Replacement:=" ", LookAt:=xlPart, SearchOrder:=xlByRows, MatchCase:=False ' Replace all Tabs in cells to Space to prevent Double Quotes occuring in the final paste text Selection.Copy MsgBox "SQL Code has been added to clipboard - Please Paste into SSMS window", vbOKOnly, "Transfer to SQL" Application.DisplayAlerts = False ' Temporarily switch off Display Alerts ActiveWindow.Close ' Delete newly created worksheet Application.DisplayAlerts = True ' Switch display alerts back on End Sub Function fn_ColLetter(Col As Integer) As String Dim strColLetter As String If Col > 26 Then ' double letter columns strColLetter = Chr(Int((Col - 1) / 26) + 64) & _ Chr(((Col - 1) Mod 26) + 65) Else ' single letter columns strColLetter = Chr(Col + 64) End If fn_ColLetter = strColLetter End Function
高强
- 在Excel中,突出显示并复制要粘贴到SQL中的数据。
SQL
- 用所需的列名创build表,并给你一个表名。 *确保
Identity Specification
是,所以它会自动增加您的身份列。 - find您的表格,然后右键单击它,然后从对话框中select“
Edit Top 200 Rows
”。 - 右键单击具有*符号的空行,然后从对话框中select粘贴
为什么不在SSMS中使用导出/导入向导?
你不能使用VBA代码从Excel中复制并粘贴到SSMS操作中吗?