文件常用操作
文件路径
1、相对目录
当前程序的目录:“.“
当前程序的目录的上一级:“..“
当前程序的目录的磁盘父目录:“\\“
2、绝对路径
尽量用Path.Combine(),可以跨平台使用而不会出错
如果在Windows上使用:
Path.Combine("A","B"); //A,B都是单个单词
Path.Combine("A","B\\C\\D");
Path.Combine("A","\\B\\C\\D"); //得到的是 \\B\\C\\D ,所以需要注意:不要B钱前面的\\
本地文件处理
1、删除文件/文件夹
当服务器上某些文件太多了,需要删除超过一定时间的文件
if(Directory.Exists(yourPath)) { //获取指定路径下所有文件夹 string[] folderPaths = Directory.GetDirectories(yourPath); foreach(string folderPath in folderPaths) Directory.Delete(folderPath, true); //获取指定路径下所有文件 string[] filePaths = Directory.GetFiles(yourPath); foreach(string filePath in filePaths) File.Delete(filePath); } //或者 DirectoryInfo folder = new DirectoryInfo(selectPath); txtFilesPath.Text = selectPath; foreach (FileInfo file in folder.GetFiles()) { //删除超过一定时间的文件 if ((DateTime.Today - file.CreationTime).TotalDays > dayCount) { File.Delete(file.FullName); }
如果你需要连你指定的文件夹一起删除 就简单的多 如下
if(Directory.Exists(yourPath)){
Directory.Delete(yourPath,true);
}
上述两例中的yourPath应为指定文件夹的路径 如: D:\test
第一例则会删除test文件夹下的所有子项
第二例则是test文件夹及其子项一起删除 需要注意的是Directory.Delete方法有两个重载 举例说明:
Directory.Delete(yourPath); //如果yourPath有子项 则删除失败 抛出异常
Directory.Delete(yourPath,true); //第二个为bool类型参数 表示是否需要使用递归删除
补充说明 如果只是需要删除文件 就使用File类 如下
if(File.Exists(filePath))
File.Delete(filePath)
上例中的filePath为文件的完整路径 如: C:\test\test.txt
2、文件/目录复制
文件的复制操作也是文件处理过程中常用的操作,文件复制比较简单,File类中提供了很多方法,这里只实例演示File.Copy()的用法,其代码如下:
string pLocalFilePath ="";//要复制的文件路径 string pSaveFilePath ="";//指定存储的路径 if (File.Exists(pLocalFilePath))//必须判断要复制的文件是否存在 { File.Copy(pLocalFilePath, pSaveFilePath, true);//三个参数分别是源文件路径,存储路径,若存储路径有相同文件是否替换 }
Directory只提供了Move移动文件夹的方法,没有提供复制的方法。
复制文件夹中的所有文件到指定目录,只需循环遍历文件夹中的所有文件即可,不过需要考虑文件夹中有下层文件夹的情况,其示例代码如下:
/// <summary> /// 复制文件夹中的所有内容 /// </summary> /// <param name="sourceDirPath">源文件夹目录</param> /// <param name="saveDirPath">指定文件夹目录</param> public void CopyDirectory(string sourceDirPath, string saveDirPath) { try { if (!Directory.Exists(saveDirPath)) { Directory.CreateDirectory(saveDirPath); } string[] files = Directory.GetFiles(sourceDirPath); foreach (string file in files) { string pFilePath = saveDirPath + "\\" + Path.GetFileName(file); if (File.Exists(pFilePath)) continue; File.Copy(file, pFilePath, true); } string[] dirs = Directory.GetDirectories(sourceDirPath); foreach (string dir in dirs) { CopyDirectory(dir, saveDirPath + "\\" + Path.GetFileName(dir)); } } catch (Exception ex) { } }
3、Excel
1.Excel中以\t做为列分隔符,换行符作为行分隔符
使用c#导出excel的时候,当数字太长时,如身份证号,导出后的excel就会显示为科学计数法。如“511122154712121000”会显示成“5.111E+1”。
解决方法是在文本前添加一个单引号。如“'511122154712121000”。导出后显示就正常了。
2.C#读写Excel的几种方法
- 使用Office自带的库:Microsoft.Office.Interop.Excel,前提是本机须安装office才能运行,且不同的office版本之间可能会有兼容问题
- 使用NPOI ,地址:https://github.com/tonyqus/npoi 在不安装office的时候也是可以读写的,速度很快,从Nuget下载 NPOI
快速Start:Read and Write Excel file in C# .NET Core using NPOI
4、CSV
CSV文件默认以英文逗号做为列分隔符,换行符作为行分隔符
将数据写入到CSV文件中--出现“科学计数法”
解决:在数据后面加上"\t"就可以。形成\t
远程文件处理
1、获取文件字节流
远程http(s)文件
HttpWebResponse.ContentLength 报异常:算术运算导致溢出
改为:
using (HttpWebResponse wr = (HttpWebResponse)req.GetResponse()) { Stream stream = wr.GetResponseStream(); //读取到内存 MemoryStream stmMemory = new MemoryStream(); byte[] buffer1 = new byte[1024 * 100]; int i; //将字节逐个放入到Byte 中 while ((i = stream.Read(buffer1, 0, buffer1.Length)) > 0) { stmMemory.Write(buffer1, 0, i); } arraryByte = stmMemory.ToArray(); stmMemory.Close(); stream.Close(); }
2、web文件上传,webapi后台接收
后台
public string Post() { string key = HttpContext.Current.Request["key"]; string value = HttpContext.Current.Request["value"]; HttpFileCollection files = HttpContext.Current.Request.Files; foreach (string f in files.AllKeys) { HttpPostedFile file = files[f]; if (string.IsNullOrEmpty(file.FileName) == false) file.SaveAs(HttpContext.Current.Server.MapPath("~/App_Data/") + file.FileName); } return key + value; }
前端
<!DOCTYPE html> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title></title> </head> <body> <form name="form" action="http://localhost:31855/api/values" method="post" enctype="multipart/form-data"> <input type="text" name="key" id="txtKey" /> <br /> <input type="text" name="value" id="txtValue" /> <br /> <input type="file" name="file" id="upFile" /> <input type="file" name="file2" id="File1" /> <br /> <input type="submit" id="btnSubmit" value="Submit" /> </form> </body> </html>
3、使用FormData对象实现ajax提交表单及文件上传,api处理
1、html代码
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title>文件上传表单ajax提交模拟</title> </head> <body> <form id="postForm"> <h2>文件上传表单ajax提交模拟</h2> <p> ajax提交给后端WebAPI处理,进而交给别人提供的第三方接口处理 </p> <p>文件名:<input type="text" name="filename" /></p> <p> 文件: <input type="file" name="my_file" /></p> <input type="button" value="提交" onclick="btnPost()" /> </form> </body> </html>
2、jquery代码:
<script src="Scripts/jquery-3.3.1.min.js"></script> <script> function btnPost() { var formData = new FormData($("#postForm")[0]); $.ajax({ url: "http://localhost/uploadfile/api/UpFile", data: formData, type: "POST", contentType: false, processData: false, success: function (msg) { alert(msg); }, error: function (e) { } }); } </script>
3、后台webapi处理
[HttpPost] public FileUploadResult UploadFile() { var name = HttpContext.Current.Request.Form["filename"]; //手动填写的文件名 if (HttpContext.Current.Request.Files.Count <= 0) { return new FileUploadResult() { ErrorMessage = "沒有文件" }; } var postFile = HttpContext.Current.Request.Files[0]; var fileName = postFile.FileName; //实际的文件名(含扩展名) var ext = Path.GetExtension(fileName).Substring(1); fileName = DateTime.Now.ToString("yyyyMMddHHssmmfff") + "." + fileName; //Stream转为byte[] //byte[] fileBytes = null; //using (var ms = new MemoryStream()) //{ // postFile.InputStream.CopyTo(ms); // fileBytes = ms.ToArray(); //} //或者 byte[] fileBytes = new byte[postFile.InputStream.Length]; postFile.InputStream.Read(fileBytes, 0, fileBytes.Length); var uploadResult = new EditFile().UploadFile(fileName, fileBytes); if (uploadResult.success) { return new FileUploadResult() { success =true,clientUrl=uploadResult.clientUrl }; } else { return new FileUploadResult() { success = false, clientUrl = uploadResult.ErrorMessage }; } }
进一步处理代码省略..
using (HttpWebResponse wr = (HttpWebResponse)req.GetResponse()) { Stream stream = wr.GetResponseStream(); //读取到内存 MemoryStream stmMemory = new MemoryStream(); byte[] buffer1 = new byte[1024 * 100]; int i; //将字节逐个放入到Byte 中 while ((i = stream.Read(buffer1, 0, buffer1.Length)) > 0) { stmMemory.Write(buffer1, 0, i); } arraryByte = stmMemory.ToArray(); stmMemory.Close(); stream.Close(); }
4、FTP文件下载
从FTP文件服务器中下载文件,含用户名和密码
/// <summary> /// 下载图片保存在本地 /// </summary> /// <param name="filePath">文件全路径</param> /// <param name="fileName">取出IP和port的文件路径和文件名</param> /// <param name="ftpUserID">FTP站点用户名</param> /// <param name="ftpPassword">TFP站点密码</param> /// <returns></returns> public static bool Download(string filePath, string fileName, string ftpUserID, string ftpPassword) { string serverPath = HttpContext.Current.Server.MapPath("/"); string subserverPath = serverPath.Substring(0, serverPath.Length - 1); string localPath = subserverPath + fileName; //含文件名的全路径 string path = Path.GetDirectoryName(localPath); //不含文件名的路径 FtpWebRequest reqFTP; try { // FileStream outputStream = new FileStream(fileName, FileMode.Create); FileStream outputStream; reqFTP = (FtpWebRequest)FtpWebRequest.Create(new Uri(filePath)); reqFTP.Method = WebRequestMethods.Ftp.DownloadFile; reqFTP.UseBinary = true; reqFTP.UsePassive = false; reqFTP.Credentials = new NetworkCredential(ftpUserID, ftpPassword); FtpWebResponse response = (FtpWebResponse)reqFTP.GetResponse(); Stream ftpStream = response.GetResponseStream(); if (File.Exists(localPath)) { outputStream = File.Open(localPath, FileMode.Open, FileAccess.ReadWrite); } else { if (!Directory.Exists(path)) { Directory.CreateDirectory(path); } outputStream = File.Create(localPath); } long cl = response.ContentLength; int bufferSize = 2048; int readCount; byte[] buffer = new byte[bufferSize]; readCount = ftpStream.Read(buffer, 0, bufferSize); while (readCount > 0) { outputStream.Write(buffer, 0, readCount); readCount = ftpStream.Read(buffer, 0, bufferSize); } ftpStream.Close(); outputStream.Close(); response.Close(); return true; } catch (Exception ex) { return false; throw new Exception("FtpHelper Download Error --> " + ex.Message); } }