免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
1234下一页
最近访问板块 发新帖
查看: 9030 | 回复: 30
打印 上一主题 下一主题

[函数] 要写一个file_copy函数 [复制链接]

论坛徽章:
769
金牛座
日期:2014-02-26 17:49:58水瓶座
日期:2014-02-26 18:10:15白羊座
日期:2014-04-15 19:29:52寅虎
日期:2014-04-17 19:43:21酉鸡
日期:2014-04-19 21:24:10子鼠
日期:2014-04-22 13:55:24卯兔
日期:2014-04-22 14:20:58亥猪
日期:2014-04-22 16:13:09狮子座
日期:2014-05-05 22:31:17摩羯座
日期:2014-05-06 10:32:53处女座
日期:2014-05-12 09:23:11子鼠
日期:2014-05-21 18:21:27
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2015-01-13 21:15 |只看该作者 |倒序浏览
能同时适用于Windows和Linux
Windows下有CopyFile函数,Linux有类似的吗?SendFile?
自己写的话用fopen fread fwrite fclose或C++的filestream,
又怕自己写的效率不好或异常处理写得不完善。
有什么好的建议吗?万分感谢!

论坛徽章:
44
15-16赛季CBA联赛之浙江
日期:2021-10-11 02:03:59程序设计版块每日发帖之星
日期:2016-07-02 06:20:0015-16赛季CBA联赛之新疆
日期:2016-04-25 10:55:452016科比退役纪念章
日期:2016-04-23 00:51:2315-16赛季CBA联赛之山东
日期:2016-04-17 12:00:2815-16赛季CBA联赛之福建
日期:2016-04-12 15:21:2915-16赛季CBA联赛之辽宁
日期:2016-03-24 21:38:2715-16赛季CBA联赛之福建
日期:2016-03-18 12:13:4015-16赛季CBA联赛之佛山
日期:2016-02-05 00:55:2015-16赛季CBA联赛之佛山
日期:2016-02-04 21:11:3615-16赛季CBA联赛之天津
日期:2016-11-02 00:33:1215-16赛季CBA联赛之浙江
日期:2017-01-13 01:31:49
2 [报告]
发表于 2015-01-13 21:38 |只看该作者
用C++你可以这么写

  1. std::ifstream src("src_path", std::ios::binary);
  2. std::ofstream dest("dest_path", std::ios::binary);
  3. dest << src.rdbuf();
复制代码

论坛徽章:
769
金牛座
日期:2014-02-26 17:49:58水瓶座
日期:2014-02-26 18:10:15白羊座
日期:2014-04-15 19:29:52寅虎
日期:2014-04-17 19:43:21酉鸡
日期:2014-04-19 21:24:10子鼠
日期:2014-04-22 13:55:24卯兔
日期:2014-04-22 14:20:58亥猪
日期:2014-04-22 16:13:09狮子座
日期:2014-05-05 22:31:17摩羯座
日期:2014-05-06 10:32:53处女座
日期:2014-05-12 09:23:11子鼠
日期:2014-05-21 18:21:27
3 [报告]
发表于 2015-01-13 21:53 |只看该作者
本帖最后由 Herowinter 于 2015-01-13 21:55 编辑

回复 2# windoze

多谢,那异常处理怎么写呢?
是不是都要自己一个个来验证实现,不像windows那样检查一下
FileCopy的返回值就好了?

论坛徽章:
44
15-16赛季CBA联赛之浙江
日期:2021-10-11 02:03:59程序设计版块每日发帖之星
日期:2016-07-02 06:20:0015-16赛季CBA联赛之新疆
日期:2016-04-25 10:55:452016科比退役纪念章
日期:2016-04-23 00:51:2315-16赛季CBA联赛之山东
日期:2016-04-17 12:00:2815-16赛季CBA联赛之福建
日期:2016-04-12 15:21:2915-16赛季CBA联赛之辽宁
日期:2016-03-24 21:38:2715-16赛季CBA联赛之福建
日期:2016-03-18 12:13:4015-16赛季CBA联赛之佛山
日期:2016-02-05 00:55:2015-16赛季CBA联赛之佛山
日期:2016-02-04 21:11:3615-16赛季CBA联赛之天津
日期:2016-11-02 00:33:1215-16赛季CBA联赛之浙江
日期:2017-01-13 01:31:49
4 [报告]
发表于 2015-01-13 21:56 |只看该作者
回复 3# Herowinter

你在外面加个try/catch不就行了

论坛徽章:
769
金牛座
日期:2014-02-26 17:49:58水瓶座
日期:2014-02-26 18:10:15白羊座
日期:2014-04-15 19:29:52寅虎
日期:2014-04-17 19:43:21酉鸡
日期:2014-04-19 21:24:10子鼠
日期:2014-04-22 13:55:24卯兔
日期:2014-04-22 14:20:58亥猪
日期:2014-04-22 16:13:09狮子座
日期:2014-05-05 22:31:17摩羯座
日期:2014-05-06 10:32:53处女座
日期:2014-05-12 09:23:11子鼠
日期:2014-05-21 18:21:27
5 [报告]
发表于 2015-01-13 22:33 |只看该作者
回复 4# windoze

再次感谢您的指点,但这样就相当于我要自己把FileCopy再实现一遍,
常见的可能出现的异常都要考虑的。

论坛徽章:
17
处女座
日期:2013-08-27 09:59:352015亚冠之柏太阳神
日期:2015-07-30 10:16:402015亚冠之萨济拖拉机
日期:2015-07-29 18:58:182015年亚洲杯之巴勒斯坦
日期:2015-03-06 17:38:17摩羯座
日期:2014-12-11 21:31:34戌狗
日期:2014-07-20 20:57:32子鼠
日期:2014-05-15 16:25:21亥猪
日期:2014-02-11 17:32:05丑牛
日期:2014-01-20 15:45:51丑牛
日期:2013-10-22 11:12:56双子座
日期:2013-10-18 16:28:17白羊座
日期:2013-10-18 10:50:45
6 [报告]
发表于 2015-01-13 22:53 |只看该作者
回复 1# Herowinter


    如果有系统调用最好还是用系统调用,自己写代码实现的文件copy需要在程序在用户态和内核态频繁的切换,文件大了这个开销是很可观的。可以参数下面的代码:
  1. #include <fcntl.h>
  2. #include <unistd.h>
  3. #if defined(__APPLE__) || defined(__FreeBSD__)
  4. #include <copyfile.h>
  5. #else
  6. #include <sys/sendfile.h>
  7. #endif

  8. int OSCopyFile(const char* source, const char* destination)
  9. {   
  10.     int input, output;   
  11.     if ((input = open(source, O_RDONLY)) == -1)
  12.     {
  13.         return -1;
  14.     }   
  15.     if ((output = open(destination, O_RDWR | O_CREAT)) == -1)
  16.     {
  17.         close(input);
  18.         return -1;
  19.     }

  20.     //Here we use kernel-space copying for performance reasons
  21. #if defined(__APPLE__) || defined(__FreeBSD__)
  22.     //fcopyfile works on FreeBSD and OS X 10.5+
  23.     int result = fcopyfile(input, output, 0, COPYFILE_ALL);
  24. #else
  25.     //sendfile will work with non-socket output (i.e. regular file) on Linux 2.6.33+
  26.     off_t bytesCopied = 0;
  27.     struct stat fileinfo = {0};
  28.     fstat(input, &fileinfo);
  29.     int result = sendfile(output, input, &bytesCopied, fileinfo.st_size);
  30. #endif

  31.     close(input);
  32.     close(output);

  33.     return result;
  34. }
复制代码
引用自:http://stackoverflow.com/questio ... ile-on-unix-using-c

论坛徽章:
769
金牛座
日期:2014-02-26 17:49:58水瓶座
日期:2014-02-26 18:10:15白羊座
日期:2014-04-15 19:29:52寅虎
日期:2014-04-17 19:43:21酉鸡
日期:2014-04-19 21:24:10子鼠
日期:2014-04-22 13:55:24卯兔
日期:2014-04-22 14:20:58亥猪
日期:2014-04-22 16:13:09狮子座
日期:2014-05-05 22:31:17摩羯座
日期:2014-05-06 10:32:53处女座
日期:2014-05-12 09:23:11子鼠
日期:2014-05-21 18:21:27
7 [报告]
发表于 2015-01-13 23:00 |只看该作者
回复 6# myworkstation


非常感谢,很详细的代码,愁了一整天了。

论坛徽章:
44
15-16赛季CBA联赛之浙江
日期:2021-10-11 02:03:59程序设计版块每日发帖之星
日期:2016-07-02 06:20:0015-16赛季CBA联赛之新疆
日期:2016-04-25 10:55:452016科比退役纪念章
日期:2016-04-23 00:51:2315-16赛季CBA联赛之山东
日期:2016-04-17 12:00:2815-16赛季CBA联赛之福建
日期:2016-04-12 15:21:2915-16赛季CBA联赛之辽宁
日期:2016-03-24 21:38:2715-16赛季CBA联赛之福建
日期:2016-03-18 12:13:4015-16赛季CBA联赛之佛山
日期:2016-02-05 00:55:2015-16赛季CBA联赛之佛山
日期:2016-02-04 21:11:3615-16赛季CBA联赛之天津
日期:2016-11-02 00:33:1215-16赛季CBA联赛之浙江
日期:2017-01-13 01:31:49
8 [报告]
发表于 2015-01-14 00:45 |只看该作者
回复 6# myworkstation


   
如果有系统调用最好还是用系统调用,自己写代码实现的文件copy需要在程序在用户态和内核态频繁的切换,文件大了这个开销是很可观的。可以参数下面的代码:


copyfile/fcopyfile是C库函数,不是系统调用,sendfile倒是系统调用,但只能在Linux下拿来拷文件。

论坛徽章:
769
金牛座
日期:2014-02-26 17:49:58水瓶座
日期:2014-02-26 18:10:15白羊座
日期:2014-04-15 19:29:52寅虎
日期:2014-04-17 19:43:21酉鸡
日期:2014-04-19 21:24:10子鼠
日期:2014-04-22 13:55:24卯兔
日期:2014-04-22 14:20:58亥猪
日期:2014-04-22 16:13:09狮子座
日期:2014-05-05 22:31:17摩羯座
日期:2014-05-06 10:32:53处女座
日期:2014-05-12 09:23:11子鼠
日期:2014-05-21 18:21:27
9 [报告]
发表于 2015-01-14 19:02 |只看该作者
@myworkstation@windoze
根据大神们的指点,今天把Design文档写好了.总结了下,应该有这几种方法:
(1)read write
(2)sendfile copyfile
(3)ifstream ofstream
(4)system("cp src target")
(5)algorithm copy

希望明天review的时候能过关, 不要都否了就好.
再次感谢帮助.

论坛徽章:
17
处女座
日期:2013-08-27 09:59:352015亚冠之柏太阳神
日期:2015-07-30 10:16:402015亚冠之萨济拖拉机
日期:2015-07-29 18:58:182015年亚洲杯之巴勒斯坦
日期:2015-03-06 17:38:17摩羯座
日期:2014-12-11 21:31:34戌狗
日期:2014-07-20 20:57:32子鼠
日期:2014-05-15 16:25:21亥猪
日期:2014-02-11 17:32:05丑牛
日期:2014-01-20 15:45:51丑牛
日期:2013-10-22 11:12:56双子座
日期:2013-10-18 16:28:17白羊座
日期:2013-10-18 10:50:45
10 [报告]
发表于 2015-01-14 21:43 |只看该作者
回复 8# windoze


   嗯,没有全平台通用的系统接口来实现这个功能,只能自己去做适配。
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP