using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Collections;using System.Data;using System.IO;using System.Reflection;using System.ComponentModel;
namespace Neusoft.Core.Neusoft.Core.Utils{ /// <summary> /// //读CSV文件类,读取指定的CSV文件,可以导出DataTable..........add by chujianqin /// </summary> public class CsvStreamReader { private ArrayList rowAL; //行链表,CSV文件的每一行就是一个链 private string fileName; //文件名 public DataTable csvDT = new DataTable(); private Encoding encoding; //编码 public DataTable table = new DataTable(); bool IsFirst = true; List<ArrayList> arry = new List<ArrayList>(); public CsvStreamReader() { this.rowAL = new ArrayList(); this.fileName = ""; this.encoding = Encoding.Default; }
/// <summary> /// /// </summary> /// <param name="fileName">文件名,包括文件路径</param> public CsvStreamReader(string fileName) { this.rowAL = new ArrayList(); this.fileName = fileName; this.encoding = Encoding.Default; LoadCsvFile(); DataView dataView = csvDT.DefaultView; dataView.Sort = "ID desc"; csvDT = dataView.ToTable(); }
/// <summary> /// /// </summary> /// <param name="fileName">文件名,包括文件路径</param> /// <param name="encoding">文件编码</param> public CsvStreamReader(string fileName, Encoding encoding) { this.rowAL = new ArrayList(); this.fileName = fileName; this.encoding = encoding; LoadCsvFile(); }
/// <summary> /// 载入CSV文件 /// </summary> private void LoadCsvFile() { //对数据的有效性进行验证
if (this.fileName == null) { throw new Exception("请指定要载入的CSV文件名"); } else if (!File.Exists(this.fileName)) { throw new Exception("指定的CSV文件不存在"); } else { } if (this.encoding == null) { this.encoding = Encoding.Default; } DataTable dt = new DataTable(); StreamReader sr = new StreamReader(this.fileName, this.encoding); string csvDataLine;
csvDataLine = ""; while (true) { string fileDataLine;
fileDataLine = sr.ReadLine(); if (fileDataLine == null) { break; } if (csvDataLine == "") { csvDataLine = fileDataLine;//GetDeleteQuotaDataLine(fileDataLine); } else { csvDataLine += "\r\n" + fileDataLine;//GetDeleteQuotaDataLine(fileDataLine); } //如果包含偶数个引号,说明该行数据中出现回车符或包含逗号 if (!IfOddQuota(csvDataLine)) { AddNewDataLine(csvDataLine);
csvDataLine = ""; } } sr.Close(); //数据行出现奇数个引号 if (csvDataLine.Length > 0) { throw new Exception("CSV文件的格式有错误"); } }
/// <summary> /// 获取两个连续引号变成单个引号的数据行 /// </summary> /// <param name="fileDataLine">文件数据行</param> /// <returns></returns> private string GetDeleteQuotaDataLine(string fileDataLine) { return fileDataLine.Replace("\"\"", "\""); }
/// <summary> /// 判断字符串是否包含奇数个引号 /// </summary> /// <param name="dataLine">数据行</param> /// <returns>为奇数时,返回为真;否则返回为假</returns> private bool IfOddQuota(string dataLine) { int quotaCount; bool oddQuota;
quotaCount = 0; for (int i = 0; i < dataLine.Length; i++) { if (dataLine[i] == '\"') { quotaCount++; } }
oddQuota = false; if (quotaCount % 2 == 1) { oddQuota = true; }
return oddQuota; }
/// <summary> /// 判断是否以奇数个引号开始
/// </summary> /// <param name="dataCell"></param> /// <returns></returns> private bool IfOddStartQuota(string dataCell) { int quotaCount; bool oddQuota;
quotaCount = 0; for (int i = 0; i < dataCell.Length; i++) { if (dataCell[i] == '\"') { quotaCount++; } else { break; } }
oddQuota = false; if (quotaCount % 2 == 1) { oddQuota = true; }
return oddQuota; }
/// <summary> /// 判断是否以奇数个引号结尾 /// </summary> /// <param name="dataCell"></param> /// <returns></returns> private bool IfOddEndQuota(string dataCell) { int quotaCount; bool oddQuota;
quotaCount = 0; for (int i = dataCell.Length - 1; i >= 0; i--) { if (dataCell[i] == '\"') { quotaCount++; } else { break; } }
oddQuota = false; if (quotaCount % 2 == 1) { oddQuota = true; }
return oddQuota; }
/// <summary> /// 加入新的数据行 /// </summary> /// <param name="newDataLine">新的数据行</param> private void AddNewDataLine(string newDataLine) { int Column = 0; DataRow Row = csvDT.NewRow(); ArrayList colAL = new ArrayList(); string[] dataArray = newDataLine.Split(','); bool oddStartQuota; //是否以奇数个引号开始 string cellData;
oddStartQuota = false; cellData = ""; for (int j = 0; j < dataArray.Length; j++) { if (IsFirst) { DataColumn dc = new DataColumn(dataArray[j]); csvDT.Columns.Add(dc); } else { if (oddStartQuota) { //因为前面用逗号分割,所以要加上逗号 cellData += "," + dataArray[j]; //是否以奇数个引号结尾 if (IfOddEndQuota(dataArray[j])) {
Row[Column] = GetHandleData(cellData); Column++; oddStartQuota = false; continue; } } else { //是否以奇数个引号开始 if (IfOddStartQuota(dataArray[j])) { //是否以奇数个引号结尾,不能是一个双引号,并且不是奇数个引号
if (IfOddEndQuota(dataArray[j]) && dataArray[j].Length > 2 && !IfOddQuota(dataArray[j])) {
Row[Column] = GetHandleData(dataArray[j]); Column++; oddStartQuota = false; continue; } else { oddStartQuota = true; cellData = dataArray[j]; continue; } } else { Row[Column] = GetHandleData(dataArray[j]); Column++; } } } } if (!IsFirst) { this.csvDT.Rows.Add(Row); } IsFirst = false; if (oddStartQuota) { throw new Exception("数据格式有问题"); }
}
/// <summary> /// 去掉格子的首尾引号,把双引号变成单引号
/// </summary> /// <param name="fileCellData"></param> /// <returns></returns> private string GetHandleData(string fileCellData) { if (fileCellData == "") { return ""; } if (IfOddStartQuota(fileCellData)) { if (IfOddEndQuota(fileCellData)) { return fileCellData.Substring(1, fileCellData.Length - 2).Replace("\"\"", "\""); //去掉首尾引号,然后把双引号变成单引号 } else { throw new Exception("数据引号无法匹配" + fileCellData); } } else { //考虑形如"" """" """""" if (fileCellData.Length > 2 && fileCellData[0] == '\"') { fileCellData = fileCellData.Substring(1, fileCellData.Length - 2).Replace("\"\"", "\""); //去掉首尾引号,然后把双引号变成单引号 } }
return fileCellData; } }
}
转载于:https://www.cnblogs.com/chujianqinlogs/p/6429198.html