科学网

 找回密码
  注册

tag 标签: delete

相关帖子

版块 作者 回复/查看 最后发表

没有相关内容

相关日志

IDL:删除影像中的波段
lixujeremy 2014-10-19 09:16
问题:删除影像中的若干波段,并生成新影像文件? 方法: IDL 。练习数据中, test.tif 包含 13 个波段,删除其中的 1~N (小于 13 )个波段,得到结果 result.tif 。 附上练习数据及代码( Practice.rar )。
个人分类: ENVI/IDL|5240 次阅读|0 个评论
[转载]强制清空回收站-ubuntu
plgongcat 2014-8-27 16:39
强制清空回收站-ubuntu 12.04 平时在ubuntu工作,会遇到不用的文件,直接delete不要以为她就消失了,其实她在Trash之中。这个 与win下的类似,ok,那么就有必要清理干净(占空间)! two-steps: ubuntu 12.04 回收站的路径 $cd HOME/.local/share/Trash/ ubuntu 12.04 强制清空回收站: $sudo rm -fr $HOME/.local/share/Trash/* 这样就清除了。
个人分类: unbutu常见问题|4333 次阅读|0 个评论
[转载]malloc/free与new/delete的区别
Tingella 2014-8-7 16:12
malloc/free与new/delete的区别 相同点 :都可用于申请动态内存和释放内存 不同点 : (1) 操作对象有所不同 。 malloc与free是C++/C 语言的标准库函数,new/delete 是C++的运算符。对于非内部数据类的对象而言,光用maloc/free 无法满足动态对象的要求。对象在创建的同时要自动执行构造函数, 对象消亡之前要自动执行析构函数。由于malloc/free 是库函数而不是运算符,不在编译器控制权限之内,不能够把执行构造函数和析构函数的任务强加malloc/free。 (2)用法上也有所不同 。 函数malloc 的原型如下: void * malloc(size_t size); 用malloc 申请一块长度为length 的整数类型的内存,程序如下: int *p = (int *) malloc(sizeof(int) * length); 我们应当把注意力集中在两个要素上:“类型转换”和“sizeof”。 1、malloc 返回值的类型是void *,所以在调用malloc 时要显式地进行类型转换,将void * 转换成所需要的指针类型。 2、 malloc 函数本身并不识别要申请的内存是什么类型,它只关心内存的总字节数。 函数free 的原型如下: void free( void * memblock ); 为什么free 函数不象malloc 函数那样复杂呢?这是因为指针p 的类型以及它所指的内存的容量事先都是知道的,语句free(p)能正确地释放内存。如果p 是NULL 指针,那么free 对p 无论操作多少次都不会出问题。如果p 不是NULL 指针,那么free 对p连续操作两次就会导致程序运行错误。 new/delete 的使用要点: 运算符new 使用起来要比函数malloc 简单得多,例如: int *p1 = (int *)malloc(sizeof(int) * length); int *p2 = new int ; 这是因为new 内置了sizeof、类型转换和类型安全检查功能。对于非内部数据类型的对象而言,new 在创建动态对象的同时完成了初始化工作。如果对象有多个构造函数,那么new 的语句也可以有多种形式。 如果用new 创建对象数组,那么只能使用对象的无参数构造函数。例如 Obj *objects = new Obj ; // 创建100 个动态对象 不能写成 Obj *objects = new Obj (1); // 创建100 个动态对象的同时赋初值1 在用delete 释放对象数组时,留意不要丢了符号‘ objects; // 正确的用法 delete objects; // 错误的用法 后者相当于delete objects ,漏掉了另外99 个对象。 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 1、new自动计算需要分配的空间,而malloc需要手工计算字节数 2、new是类型安全的,而malloc不是,比如: int* p = new float ; // 编译时指出错误 int* p = malloc(2*sizeof(float)); // 编译时无法指出错误 new operator 由两步构成,分别是 operator new 和 construct 3、operator new对应于malloc,但operator new可以重载,可以自定义内存分配策略,甚至不做内存分配,甚至分配到非内存设备上。而malloc无能为力 4、new将调用constructor,而malloc不能;delete将调用destructor,而free不能。 5、malloc/free要库文件支持,new/delete则不要。 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 1、本质区别 malloc/free是C/C++语言的标准库函数,new/delete是C++的运算符。 对于用户自定义的对象而言,用maloc/free无法满足动态管理对象的要求。对象在创建的同时要自动执行构造函数,对象在消亡之前要自动执行析构函数。由于malloc/free是库函数而不是运算符,不在编译器控制权限之内,不能够把执行构造函数和析构函数的任务强加于malloc/free。因此C++需要一个能完成动态内存分配和初始化工作的运算符new,以及一个能完成清理与释放内存工作的运算符delete。 view plain copy class Obj { public : Obj( ) { cout Initialization endl; } ~ Obj( ) { cout Destroy endl; } void Initialize( ) { cout Initialization endl; } void Destroy( ) { cout Destroy endl; } }obj; void UseMallocFree( ) { Obj * a = (Obj *) malloc( sizeof ( obj ) ); // allocate memory a - Initialize(); // initialization // … a - Destroy(); // deconstruction free(a); // release memory } void UseNewDelete( void ) { Obj * a = new Obj; // … delete a; } 类Obj的函数Initialize实现了构造函数的功能,函数Destroy实现了析构函数的功能。函数UseMallocFree中,由于malloc/free不能执行构造函数与析构函数,必须调用成员函数Initialize和Destroy来完成“构造”与“析构”。所以我们不要用malloc/free来完成动态对象的内存管理,应该用new/delete。由于内部数据类型的“对象”没有构造与析构的过程,对它们而言malloc/free和new/delete是等价的。 2、联系 既然new/delete的功能完全覆盖了malloc/free,为什么C++还保留malloc/free呢?因为C++程序经常要调用C函数,而C程序只能用malloc/free管理动态内存。如果用free释放“new创建的动态对象”,那么该对象因无法执行析构函数而可能导致程序出错。如果用delete释放“malloc申请的动态内存”,理论上讲程序不会出错,但是该程序的可读性很差。所以new/delete、malloc/free必须配对使用。
个人分类: C++复习|1059 次阅读|0 个评论
[转载]malloc/free与new/delete的区别
Tingella 2014-8-7 15:52
malloc/free与new/delete的区别 相同点 :都可用于申请动态内存和释放内存 不同点 : (1) 操作对象有所不同 。 malloc与free是C++/C 语言的标准库函数,new/delete 是C++的运算符。对于非内部数据类的对象而言,光用maloc/free 无法满足动态对象的要求。对象在创建的同时要自动执行构造函数, 对象消亡之前要自动执行析构函数。由于malloc/free 是库函数而不是运算符,不在编译器控制权限之内,不能够把执行构造函数和析构函数的任务强加malloc/free。 (2)用法上也有所不同 。 函数malloc 的原型如下: void * malloc(size_t size); 用malloc 申请一块长度为length 的整数类型的内存,程序如下: int *p = (int *) malloc(sizeof(int) * length); 我们应当把注意力集中在两个要素上:“类型转换”和“sizeof”。 1、malloc 返回值的类型是void *,所以在调用malloc 时要显式地进行类型转换,将void * 转换成所需要的指针类型。 2、 malloc 函数本身并不识别要申请的内存是什么类型,它只关心内存的总字节数。 函数free 的原型如下: void free( void * memblock ); 为什么free 函数不象malloc 函数那样复杂呢?这是因为指针p 的类型以及它所指的内存的容量事先都是知道的,语句free(p)能正确地释放内存。如果p 是NULL 指针,那么free 对p 无论操作多少次都不会出问题。如果p 不是NULL 指针,那么free 对p连续操作两次就会导致程序运行错误。 new/delete 的使用要点: 运算符new 使用起来要比函数malloc 简单得多,例如: int *p1 = (int *)malloc(sizeof(int) * length); int *p2 = new int ; 这是因为new 内置了sizeof、类型转换和类型安全检查功能。对于非内部数据类型的对象而言,new 在创建动态对象的同时完成了初始化工作。如果对象有多个构造函数,那么new 的语句也可以有多种形式。 如果用new 创建对象数组,那么只能使用对象的无参数构造函数。例如 Obj *objects = new Obj ; // 创建100 个动态对象 不能写成 Obj *objects = new Obj (1); // 创建100 个动态对象的同时赋初值1 在用delete 释放对象数组时,留意不要丢了符号‘ objects; // 正确的用法 delete objects; // 错误的用法 后者相当于delete objects ,漏掉了另外99 个对象。 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 1、new自动计算需要分配的空间,而malloc需要手工计算字节数 2、new是类型安全的,而malloc不是,比如: int* p = new float ; // 编译时指出错误 int* p = malloc(2*sizeof(float)); // 编译时无法指出错误 new operator 由两步构成,分别是 operator new 和 construct 3、operator new对应于malloc,但operator new可以重载,可以自定义内存分配策略,甚至不做内存分配,甚至分配到非内存设备上。而malloc无能为力 4、new将调用constructor,而malloc不能;delete将调用destructor,而free不能。 5、malloc/free要库文件支持,new/delete则不要。 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 1、本质区别 malloc/free是C/C++语言的标准库函数,new/delete是C++的运算符。 对于用户自定义的对象而言,用maloc/free无法满足动态管理对象的要求。对象在创建的同时要自动执行构造函数,对象在消亡之前要自动执行析构函数。由于malloc/free是库函数而不是运算符,不在编译器控制权限之内,不能够把执行构造函数和析构函数的任务强加于malloc/free。因此C++需要一个能完成动态内存分配和初始化工作的运算符new,以及一个能完成清理与释放内存工作的运算符delete。 view plain copy class Obj { public : Obj( ) { cout Initialization endl; } ~ Obj( ) { cout Destroy endl; } void Initialize( ) { cout Initialization endl; } void Destroy( ) { cout Destroy endl; } }obj; void UseMallocFree( ) { Obj * a = (Obj *) malloc( sizeof ( obj ) ); // allocate memory a - Initialize(); // initialization // … a - Destroy(); // deconstruction free(a); // release memory } void UseNewDelete( void ) { Obj * a = new Obj; // … delete a; } 类Obj的函数Initialize实现了构造函数的功能,函数Destroy实现了析构函数的功能。函数UseMallocFree中,由于malloc/free不能执行构造函数与析构函数,必须调用成员函数Initialize和Destroy来完成“构造”与“析构”。所以我们不要用malloc/free来完成动态对象的内存管理,应该用new/delete。由于内部数据类型的“对象”没有构造与析构的过程,对它们而言malloc/free和new/delete是等价的。 2、联系 既然new/delete的功能完全覆盖了malloc/free,为什么C++还保留malloc/free呢?因为C++程序经常要调用C函数,而C程序只能用malloc/free管理动态内存。如果用free释放“new创建的动态对象”,那么该对象因无法执行析构函数而可能导致程序出错。如果用delete释放“malloc申请的动态内存”,理论上讲程序不会出错,但是该程序的可读性很差。所以new/delete、malloc/free必须配对使用。
个人分类: C++复习|1203 次阅读|0 个评论
[转载]Jaro-Winkler Distance 浅析
wl2119 2014-6-29 22:01
Jaro-Winkler Distance 浅析 这是一种计算两个字符串之间相似度的方法,想必都听过Edit Distance,Jaro-Winkler Distance 是Jaro Distance的一个扩展,而Jaro Distance(Jaro 1989;1995)据说是用来判定健康记录上两个名字是否相同,也有说是是用于人口普查,具体干什么就不管了,让我们先来看一下Jaro Distance的定义。 两个给定字符串S1和S2的Jaro Distance为: m是匹配的字符数; t是换位的数目。 两个分别来自S1和S2的字符如果相距不超过 时,我们就认为这两个字符串是匹配的;而这些相互匹配的字符则决定了换位的数目t,简单来说就是不同顺序的匹配字符的数目的一半即为换位的数目t,举例来说, MARTHA 与 MARHTA 的字符都是匹配的,但是这些匹配的字符中,T和H要换位才能把 MARTHA 变为 MARHTA ,那么T和H就是不同的顺序的匹配字符,t=2/2=1. 那么这两个字符串的Jaro Distance即为: 而Jaro-Winkler则给予了起始部分就相同的字符串更高的分数,他定义了一个前缀p,给予两个字符串,如果前缀部分有长度为 的部分相同,则Jaro-Winkler Distance为: d j 是两个字符串的Jaro Distance 是前缀的相同的长度,但是规定最大为4 p 则是调整分数的常数,规定不能超过0.25,不然可能出现dw大于1的情况,Winkler将这个常数定义为0.1 这样,上面提及的 MARTHA 和 MARHTA 的Jaro-Winkler Distance为: d w = 0.944 + (3 * 0.1(1 − 0.944)) = 0.961 以上资料来源于维基百科: http://en.wikipedia.org/wiki/Jaro-Winkler_distance 这样一来很容易写出这个算法的代码: 1: double jaro_distance(string s1,string s2) 2: { 3: if (s1.empty()||s2.empty()) 4: { 5: if (s1.empty()s2.empty()) 6: return 1.0; 7: return 0.0; 8: } 9: int allowrange=max(s1.length(),s2.length())/2-1; 10: int i,j; 11: bool is_match=false; 12: int *matches= new int ; 13: //将s2中匹配的字符标号,这个标号的意义在于计算t的值, 14: //从前往后遍历,如果顺序不对,则肯定要调换 15: //DWAYEN 16: //0-132 这是一个matches的例子 17: //DUANE 18: for (i=0;is2.length();++i) 19: matches =-1; 20: double m=0; //匹配的数目 21: for (i=0;is1.length();++i) 22: { 23: is_match=false; 24: for (j=i;is_match==false j=0 j=i-allowrange;--j) 25: { 26: if (s2 ==s1 ) 27: { 28: matches =m++; 29: is_match=true; 30: } 31: } 32: for (j=i;is_match==false js2.length() j=i+allowrange;++j) 33: { 34: if (s2 ==s1 ) 35: { 36: matches =m++; 37: is_match=true; 38: } 39: } 40: } 41: double t=0; 42: i=0; 43: for (j=0;js2.length();++j) 44: { 45: if (matches !=-1) 46: { 47: if (matches !=i++) 48: ++t; 49: } 50: } 51: delete !=s2 ) 63: break ; 64: ++len; 65: } 66: double dj=jaro_distance(s1,s2); 67: return dj+p*len*(1-dj); 68: }
个人分类: Matlab|2992 次阅读|0 个评论
VC6调试版本C运行库内存申请的一个bug
热度 1 majian 2011-4-21 14:47
这两天调程序,遇到一个莫名奇妙的错误,程序总是在运行很长一段时间后崩溃,但是在两台机器上显示错误提示,一台机器上显示是否调试。 很无语的调了两三天了,一直没进展,最早怀疑是内存泄露的原因,后来下载了vld一点点的调,没有内存泄露了,程序照样出问题,郁闷啊。 今天早上在这台机器上发现,每次崩溃实际上都是调用了int 3中断,于是开始研究汇编,转了半天,发现晕了,上网搜,结果发现了下面这篇文章,让我ft,竟然是vc6的调试版bug ================================================================= VC调试版本C运行库内存申请的一个bug 遇到过一个通信方面的软件,需要长期运行,做压力测试时,高负荷连续运行一定天数时必定崩溃,而且都是在msvcrtd.dll中崩溃。负责维护的人百思不得其解,就去问微软的人,结果微软的人说这是VC6带的msvcrtd.dll的一个问题,VC2005已经没有这个问题了,请升级到新的版本。这个软件规模比较大,依赖于很多库,后台都是用VC6编译的调试版本,为了方便定位问题,没有Release版本。升级到VC2005后会不会出现别的问题,没有人敢冒这个风险,于是没有使用VC2005。 闲着没事的时候分析了一下,才发现问题其实很简单。msvcrtd.dll对每次内存申请都进行计数,当计数值达到设定的某个值时,就会调用_CrtDbgBreak()。MSDN对_CrtDbgBreak的说明是:Sets a break point on a particular line of code,其实_CrtDbgBreak在X86下只有一条指令就是int 3(0xCC)。 在dbgheap.c中定义了下面两个变量: static long _lRequestCurr = 1; /* Current request number */ extern "C" _CRTIMP long _crtBreakAlloc = -1L; /* Break on allocation by request number */ _lRequestCurr表示当前的申请次数,_crtBreakAlloc表示当内存申请次数达到某个值时break,即调用_CrtDbgBreak。详情可参考debugheap.c中的_heap_alloc_dbg_impl函数: lRequest = _lRequestCurr; /* break into debugger at specific memory allocation */ if (_crtBreakAlloc != -1L lRequest == _crtBreakAlloc) _CrtDbgBreak(); VC6附带的dbgheap.c中没有添加_crtBreakAlloc != -1L的判断,而是: if (lRequest == _crtBreakAlloc) _CrtDbgBreak(); _lRequestCurr初始化为1,每次申请内存都加1,当_lRequestCurr为-1时在VC6的dbgheap.c中就会触发int 3导致程序退出,而在新的版本中添加了_crtBreakAlloc != -1L的判断,所以默认的情况下是不会触发int 3 退出的。 可以通过调用_CrtSetBreakAlloc设置_crtBreakAlloc的值,当我们设置了新的_crtBreakAlloc,而且_crtBreakAlloc等于_lRequestCurr时就会触发int 3。 弄清楚了问题的所在,我们就可以着手解决问题了。VC6的dbgheap.c中有两个地方判断了lRequest 是否与_crtBreakAlloc相等,相等后执行指令int 3。我们不用复杂的处理,把int 3替换为nop(0x90)指令即可。首先得到“if (_crtBreakAlloc != -1L lRequest == _crtBreakAlloc)” 对应的二进制指令,用UE打开msvcrtd.dll,使用16进制编辑模式,查找得到的二进制指令,发现确实只有二处,把紧接着它们的0xCC替换为0x90,问题解决。 本文来自CSDN博客,转载请标明出处: http://blog.csdn.net/someonea/archive/2008/03/29/2229183.aspx ================================================ 问题还不算完,我可以用release版运算,但是总去搞release版也麻烦啊 不知道哪位大侠能告诉我 首先得到“if (_crtBreakAlloc != -1L lRequest == _crtBreakAlloc)” 对应的二进制指令 这个指令是啥么? 调程序的时候还发现介绍检测内存泄露的一篇好的博客: 关于MFC下检查和消除内存泄露的技巧 摘要 本文分析了Windows环境使用MFC调试内存泄露的技术,介绍了在Windows环境下用VC++查找,定位和消除内存泄露的方法技巧。 关键词:VC++;CRT 调试堆函数;试探法。 编译环境 VC++6.0 技术原理 检测内存泄漏的主要工具是调试器和 CRT 调试堆函数。若要启用调试堆函数,请在程序中包括以下语句: #define CRTDBG_MAP_ALLOC #include stdlib.h #include crtdbg.h 注意 #include 语句必须采用上文所示顺序。如果更改了顺序,所使用的函数可能无法正确工作。 通过包括 crtdbg.h,将 malloc 和 free 函数映射到其“Debug”版本_malloc_dbg 和_free_dbg,这些函数将跟踪内存分配和释放。此映射只在调试版本(在其中定义了 _DEBUG)中发生。发布版本使用普通的 malloc 和 free 函数。 #define 语句将 CRT 堆函数的基版本映射到对应的“Debug”版本。并非绝对需要该语句,但如果没有该语句,内存泄漏转储包含的有用信息将较少。 在添加了上面所示语句之后,可以通过在程序中包括以下语句来转储内存泄漏信息: _CrtDumpMemoryLeaks(); 当在调试器下运行程序时,_CrtDumpMemoryLeaks 将在“输出”窗口中显示内存泄漏信息。内存泄漏信息如下所示: Detected memory leaks! Dumping objects - C:PROGRAM FILESVISUAL STUDIOMyProjectsleaktestleaktest.cpp(20) : {18} normal block at 0x00780E80, 64 bytes long. Data:          CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD Object dump complete. 如果不使用 #define _CRTDBG_MAP_ALLOC 语句,内存泄漏转储如下所示: Detected memory leaks! Dumping objects - {18} normal block at 0x00780E80, 64 bytes long. Data: CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD Object dump complete. 未定义 _CRTDBG_MAP_ALLOC 时,所显示的会是: 内存分配编号(在大括号内)。 块类型(普通、客户端或 CRT)。 十六进制形式的内存位置。 以字节为单位的块大小。 前 16 字节的内容(亦为十六进制)。 定义了 _CRTDBG_MAP_ALLOC 时,还会显示在其中分配泄漏的内存的文件。文件名后括号中的数字(本示例中为 20)是该文件内的行号。 转到源文件中分配内存的行 在"输出"窗口中双击包含文件名和行号的行。 -或- 在"输出"窗口中选择包含文件名和行号的行,然后按 F4 键。 _CrtSetDbgFlag 如果程序总在同一位置退出,则调用 _CrtDumpMemoryLeaks 足够方便,但如果程序可以从多个位置退出该怎么办呢?不要在每个可能的出口放置一个对 _CrtDumpMemoryLeaks 的调用,可以在程序开始包括以下调用: _CrtSetDbgFlag ( _CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF ); 该语句在程序退出时自动调用 _CrtDumpMemoryLeaks。必须同时设置 _CRTDBG_ALLOC_MEM_DF 和 _CRTDBG_LEAK_CHECK_DF 两个位域,如上所示。 说明 在VC++6.0的环境下,不再需要额外的添加 #define CRTDBG_MAP_ALLOC #include stdlib.h #include crtdbg.h 只需要按F5,在调试状态下运行,程序退出后在"输出窗口"可以看到有无内存泄露。如果出现 Detected memory leaks! Dumping objects - 就有内存泄露。 确定内存泄露的地方 根据内存泄露的报告,有两种消除的方法: 第一种比较简单,就是已经把内存泄露映射到源文件的,可以直接在"输出"窗口中双击包含文件名和行号的行。例如 Detected memory leaks! Dumping objects - C:PROGRAM FILESVISUAL STUDIOMyProjectsleaktestleaktest.cpp(20) : {18} normal block at 0x00780E80, 64 bytes long. Data: CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD Object dump complete. C:PROGRAM FILESVISUAL STUDIOMyProjectsleaktestleaktest.cpp(20) 就是源文件名称和行号。 第二种比较麻烦,就是不能映射到源文件的,只有内存分配块号。 Detected memory leaks! Dumping objects - {18} normal block at 0x00780E80, 64 bytes long. Data: CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD CD Object dump complete.   这种情况我采用一种"试探法"。由于内存分配的块号不是固定不变的,而是每次运行都是变化的,所以跟踪起来很麻烦。但是我发现虽然内存分配的块号是变化的,但是变化的块号却总是那几个,也就是说多运行几次,内存分配的块号很可能会重复。因此这就是"试探法"的基础。 先在调试状态下运行几次程序,观察内存分配的块号是哪几个值; 选择出现次数最多的块号来设断点,在代码中设置内存分配断点: 添加如下一行(对于第 18 个内存分配): _crtBreakAlloc = 18; 或者,可以使用具有同样效果的 _CrtSetBreakAlloc 函数: _CrtSetBreakAlloc(18); 在调试状态下运行序,在断点停下时,打开"调用堆栈"窗口,找到对应的源代码处; 退出程序,观察"输出窗口"的内存泄露报告,看实际内存分配的块号是不是和预设值相同,如果相同,就找到了;如果不同,就重复步骤3,直到相同。 最后就是根据具体情况,在适当的位置释放所分配的内存。
个人分类: 技术|7889 次阅读|2 个评论

Archiver|手机版|科学网 ( 京ICP备07017567号-12 )

GMT+8, 2024-6-11 10:49

Powered by ScienceNet.cn

Copyright © 2007- 中国科学报社

返回顶部