【问题标题】:Save Excel Worksheet as CSV with null and semicolon as separator将 Excel 工作表另存为 CSV,以 null 和分号作为分隔符
【发布时间】:2012-03-16 00:36:34
【问题描述】:

我正在像这样在 C# 中导出 Excel.Worksheet:

myWorksheet.SaveAs(myPath, Excel.XlFileFormat.xlCSV);

它几乎可以正常工作,但我需要强制做两件事:

  • “字段分隔符”应为分号 (;)。我得到一个逗号 (,)
  • “文本分隔符”应始终为空。我收到双引号 ("")

The documentation 完全没有帮助(到底是什么“xlTextWindows:指定一种文本格式。”应该是什么意思?)

有什么想法吗?

【问题讨论】:

  • 你得到一个逗号作为你的字段分隔符,因为这就是 CSV 中的“c”代表的意思。尽管我不熟悉 Excel 内置格式的长长列表,但我认为您可能找不到完全适合您需要的内容。如果这是一次性操作,那么执行全局搜索和替换来完成此任务将相当简单。这是您需要反复做的事情吗?你用 C# 标记了这个——你对一些 C# 代码感兴趣吗?
  • xlTextWindows 是定义换行符的许多常量之一。 Windows 使用 CR LF。使用 Excel,将工作簿另存为 CSV 不会在文本字段周围放置双引号,除非它包含逗号。 C# 不同,或者您的字段中有逗号。我了解如果将小数分隔符指定为逗号,Excel 将使用分号作为 CSV 分隔符。这通常是一个国家设置,但 C# 具有允许临时国家设置的功能,这可能值得一试。

标签: c# excel csv


【解决方案1】:

用分号替换逗号的 VBA(不是 C#)解决方案是:

Sub CreateCSV()

Dim rCell As Range
Dim rRow As Range
Dim sOutput As String
Dim sFname As String, lFnum As Long

'Open a text file to write
sFname = "C:\MyCsv.csv"
lFnum = FreeFile

Open sFname For Output As lFnum
'Loop through the rows'
    For Each rRow In ActiveSheet.UsedRange.Rows
    'Loop through the cells in the rows'
    For Each rCell In rRow.Cells
        sOutput = sOutput & rCell.Value & ";"
    Next rCell
     'remove the last comma'
    sOutput = Left(sOutput, Len(sOutput) - 1)

    'write to the file and reinitialize the variables'
    Print #lFnum, sOutput
    sOutput = ""
 Next rRow

'Close the file'
Close lFnum

End Sub

source 经过测试并且可以工作。现在,我不确定您所说的 "" 是什么文本分隔符,但我没有遇到过。如果您采用 VBA 方式,请告诉我是否仍在发生这种情况,我们将更改代码。如果这个 VBA 解决方案对你完全没用,我很抱歉!

【讨论】:

    【解决方案2】:

    谢谢大家,但我一直在寻找不那么笨拙的东西。

    无论如何,由于我离关闭项目只有一步之遥,所以我整理了一个不优雅但有效的解决方案,如下所示:

    static public void WorksheetToCSV(Excel.Worksheet origine, string CSVoutPath, string fieldSeparator, string textSeparator)
        {
            Excel.Range rngCurrentRow;
            string lineaDaScrivere;
            TextWriter csv = new StreamWriter(CSVoutPath);
    
    
            for (int i = 1; i <= origine.UsedRange.Rows.Count; i++)
            {
                rngCurrentRow = origine.UsedRange.get_Range("A" + i, "A" + i).EntireRow;
                lineaDaScrivere="";
    
                foreach (Excel.Range cella in rngCurrentRow.Columns)
                {
                    try
                    {
                        lineaDaScrivere = lineaDaScrivere + textSeparator + cella.Value.ToString() + textSeparator + fieldSeparator;
                    }
                    catch (NullReferenceException ex)
                    {
                        break;
                    }
                }
                lineaDaScrivere=lineaDaScrivere.Substring(0, (lineaDaScrivere.Length - fieldSeparator.Length));
    
               csv.WriteLine(lineaDaScrivere);
            }
    
            csv.Close();
        }
    

    有更好的解决方案,但这对我来说按预期工作。

    【讨论】:

    • 不要编写自己的 CSV 解析器/生成器。有libraries 为您处理所有问题。在你的情况下:你没有转义你的字符,这可能导致不正确的 CSV 输出。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-06-03
    • 2011-11-11
    • 2017-11-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多