MyMSDN

MyMSDN记录开发新知道

共2页: 1 2 
@bob
我不知道您说的部分言语是哪些?另外你觉得换个什么标题比较好呢?
@溪流
是,本文要说的就是这个
@xxoo
wProcessorArchitecture
The processor architecture of the installed operating system.
re: [C++]内存管理(1) volnet 2010-07-08 11:08
@zuhd
因为我的代码用到STL的东西,所以现在替换全局new,似乎还有问题……悲剧
re: [C++]内存管理(1) volnet 2010-07-08 11:07
@zuhd
感谢您的回复。
1、我和智能指针要解决的应该是相同的问题,另外我还希望能够解决一些碎片相关的问题,虽然现在还没有做具体的代码和设计。但是如果我接管了new或者部分new的话,我就有办法去管理它们,并且动一点手脚了。现在关于是否每个分配都有正确的释放,这一点我暂时不做太多考虑了,我们现在基本用shared_ptr来做,这里就有一个问题了,我希望用我的内存分配机制去替换shared_ptr的对象存储。考虑下面的代码shared_ptr sp_(new MyClass()); 其实内存还是通过默认的operator new去分配的内存,这个内存通常是直接向操作系统去调用的,我现在希望有一块较大的内存,然后所有小块的内存分配我都希望自己来管理,而不用每次都向操作系统申请。但是现在shared_ptr在发挥作用前就已经通过new去做了内存分配,显然我自造shared_ptr是无法解决这个问题的。我不知道有没有办法转存那块内存,并立即释放掉,比如在内部通过memmove将向系统new出来的部分拷贝到我的构造中,然后将它们释放,这样我就不用替换全局的new来管理与shared_ptr有关的内存了。因为我们的代码中大部分用到了shared_ptr,所以此法能解决比较多的问题。
2、是否有其他的建议呢?
re: [C++]内存管理(1) volnet 2010-07-07 15:15
已经更新下载代码中的测试用例,现在的测试更加复杂,更具有一般性,欢迎大家下载体验,程序有些许改动,详见上一条回复:
[移除prev_chunk,next_chunk,新增near_chunk,修改remove_chunk]
源代码下载地址不变。
源代码下载:
http://www.cppblog.com/Files/mymsdn/memory_manager.rar
re: [C++]内存管理(1) volnet 2010-07-07 15:08
移除prev_chunk,next_chunk,新增near_chunk,修改remove_chunk
方法有更新,更新内容:

BOOL memory_manager::near_chunk(block_table_type &list, int offset, OUT chunk_type * prevChunk, OUT chunk_type * nextChunk)
{
block_table_type::iterator itPrev;
block_table_type::iterator itNext;

if(prevChunk == 0 || nextChunk == 0)
return FALSE;
else
{
prevChunk->status = Occupied;
nextChunk->status = Occupied;
}
if(list[offset].hHeap == 0)
return FALSE;
block_table_type::iterator it = list.find(offset);
if(it == list.end())
return FALSE;

itPrev = list.end();
itNext = list.end();

if(it != list.begin())
{
itPrev = --it;
++it;
}

if(it != list.end())
{
itNext = ++it;
--it;
}

if(itPrev != list.end())
{
prevChunk->hHeap = (itPrev)->second.hHeap;
prevChunk->pHead = (itPrev)->second.pHead;
prevChunk->size = (itPrev)->second.size;
prevChunk->status = (itPrev)->second.status;
}

if(itNext != list.end())
{
nextChunk->hHeap = (itNext)->second.hHeap;
nextChunk->pHead = (itNext)->second.pHead;
nextChunk->size = (itNext)->second.size;
nextChunk->status = (itNext)->second.status;
}
if(itPrev != list.end() || itNext != list.end())
return TRUE;
return FALSE;
}
void remove_chunk(int heapIndex, int offset)
{
chunk_type prevFreeChunk, nextFreeChunk;
if( near_chunk(heap_list[heapIndex].full_list, offset, &prevFreeChunk, &nextFreeChunk) )
{
// a) 前项检测:
// 前一项如果为Free,将前项size+=当前项size,删除当前项。
if(prevFreeChunk.status == Free && nextFreeChunk.status != Free)
{
int prevOffset = static_cast(prevFreeChunk.pHead) - static_cast(heap_list[heapIndex].pHead);
free_chunk_list_remove(heap_list[heapIndex].full_list[prevOffset].size, heap_list[heapIndex].hHeap);
heap_list[heapIndex].full_list[prevOffset].size += heap_list[heapIndex].full_list[offset].size;
free_chunk_list_add(heap_list[heapIndex].full_list[prevOffset].size, heap_list[heapIndex].hHeap);
int eraseSucceed = heap_list[heapIndex].full_list.erase(offset);
#ifdef _DEBUG
// 如果移除偏移不等于1个
if( eraseSucceed != 1)
{
_TRACE(_W("从完全列表中移除对象出现异常,移除offset为%d,移除个数为%d.\n"), offset, eraseSucceed);
}
_TRACE(_W("执行前项检测且前项状态为空闲,可执行合并。前项偏移为%d\n"), prevOffset);
#endif
}

// b) 后项检测:
// 如果后项为Free,将当前项size=size+后项size,删除后项。
else if(prevFreeChunk.status != Free && nextFreeChunk.status == Free)
{
int nextOffset = static_cast(nextFreeChunk.pHead) - static_cast(heap_list[heapIndex].pHead);
free_chunk_list_remove(heap_list[heapIndex].full_list[nextOffset].size, heap_list[heapIndex].hHeap);
heap_list[heapIndex].full_list[offset].size += heap_list[heapIndex].full_list[nextOffset].size;
free_chunk_list_add(heap_list[heapIndex].full_list[offset].size, heap_list[heapIndex].hHeap);
int eraseSucceed = heap_list[heapIndex].full_list.erase(nextOffset);
#ifdef _DEBUG
// 如果移除偏移不等于1个
if( eraseSucceed != 1)
{
_TRACE(_W("从完全列表中移除对象出现异常,移除nextOffset为%d,移除个数为%d.\n"), nextOffset, eraseSucceed);
}
_TRACE(_W("执行后项检测且后项状态为空闲,可执行合并。后项偏移为%d\n"), nextOffset);
#endif
return;
}

// c) 前后项检测:
else if(prevFreeChunk.status == Free && nextFreeChunk.status == Free)
{
int prevOffset = static_cast(prevFreeChunk.pHead) - static_cast(heap_list[heapIndex].pHead);
int nextOffset = static_cast(nextFreeChunk.pHead) - static_cast(heap_list[heapIndex].pHead);
free_chunk_list_remove(heap_list[heapIndex].full_list[nextOffset].size, heap_list[heapIndex].hHeap);
free_chunk_list_remove(heap_list[heapIndex].full_list[prevOffset].size, heap_list[heapIndex].hHeap);
heap_list[heapIndex].full_list[prevOffset].size
= heap_list[heapIndex].full_list[prevOffset].size
+ heap_list[heapIndex].full_list[offset].size
+ heap_list[heapIndex].full_list[nextOffset].size;
free_chunk_list_add(heap_list[heapIndex].full_list[prevOffset].size, heap_list[heapIndex].hHeap);
int eraseSucceed = heap_list[heapIndex].full_list.erase(offset);
eraseSucceed += heap_list[heapIndex].full_list.erase(nextOffset);
#ifdef _DEBUG
// 如果移除偏移不等于2个
if( eraseSucceed != 2)
{
_TRACE(_W("从完全列表中移除对象出现异常,移除offset为%d,移除nextOffset为%d,移除个数为%d.\n"), offset, nextOffset, eraseSucceed);
}
_TRACE(_W("执行前后项检测且前后项状态为空闲,可执行合并。\n"));
#endif
return;
}
// d) 前后项检测:
else if(prevFreeChunk.status == Occupied && nextFreeChunk.status == Occupied)
{
free_chunk_list_add(heap_list[heapIndex].full_list[offset].size, heap_list[heapIndex].hHeap);
}
else
{
_TRACE(_W("该情况不在考虑范围内。\n"));
}
}
else
{
free_chunk_list_add(heap_list[heapIndex].full_list[offset].size, heap_list[heapIndex].hHeap);
}
}
re: [C++]内存管理(1) volnet 2010-07-07 10:31
@zuhd
1、就像new和delete所面临的挑战一样,我们能保证用的时候去分配,但是通常可能因为一些原因忘记去释放这块内存,比如你已经很小心了,但是异常出现的时候,可能delete并没有执行。
2、详见上一条回复
re: [C++]内存管理(1) volnet 2010-07-07 10:30
@pcm
我的意思是,在堆中,存放的是一个对象的真实内容,在栈中存在的是存放对象内容的堆的地址,也就是一个int *p,这样,那么如果p的值在已经不在栈中了,也就是我这个管理器中还存有这个地址的相关内存的话,其实这块内存将不再被引用,就被标记为垃圾了。
re: [C++]内存管理(1) volnet 2010-07-07 08:58
@OwnWaterloo
希望您多指教啊
re: [C++]内存管理(1) volnet 2010-07-06 23:34
@OwnWaterloo
嗯,样式上,我自己有定义了几个简单的样式。windows live writer+vspaste插件用来贴代码。黄色部分的详细设计,是我之前在Word写好的,直接贴过来,可能样式略有变化。
造轮子好啊!造轮子才知道轮子有多么难造,你不造你永远不知道!
re: size_t的倒序遍历问题 volnet 2010-07-01 23:58
@OwnWaterloo
好像不错
re: size_t的倒序遍历问题 volnet 2010-07-01 14:10
@Tiger
可是我怎么看不到呢?您能截图一下么,太奇怪了
re: size_t的倒序遍历问题 volnet 2010-07-01 09:16
@egmkang
我应该没发到首页去吧,你咋能看得到呢?
re: [翻译]高效使用auto_ptr volnet 2010-04-09 10:42
@欲三更
这就是应该象是:
// stack <- dumb pointer
// dump pointer -> do()
// dump pointer -> hello();
// stack -> delete dumb pointer auto

该干嘛让他自己干嘛去,我们要做的无非就是将指针在开始的时候交给栈可管理的对象去管理……然后继续放任自由……
re: [翻译]高效使用auto_ptr volnet 2010-04-08 14:10
@Benjamin
这就是这篇文章的主题啊,除了之前提到过的几种形式,就不应该发明其它形式了……
re: 对 C++ 历史的个人观点 volnet 2010-04-07 19:17
标记一下,郁闷啊,昨天在你CSDN看的,一点注释都没有,这里原来版本有改进……还有很多回复,晚上回去洗把脸再看
@OwnWaterloo
似乎没有
很久很久以前VC的默认配置是
变量声明一定要统统放在变量定义之上
int sum = 0,value;
while(std::cin>>value) //以前很少在while里面使用这样的输入
sum += value;
std::cout << sum << endl;

//
90
80
80
6556
=
6806
re: 如何编译TrueCrypt源码 volnet 2010-03-12 16:19
@gengjl
这样做没错
re: 如何编译TrueCrypt源码 volnet 2010-03-12 16:19
@azunite
这个是一个GUID,这个ID需要我们自行定义
re: QuickSort快速排序法 volnet 2009-10-28 00:55
@bug
@bug
两位bug同学不知道是不是同一个人,在此特别感谢两位提出的意见和建议。
代码已经做了修改,详见http://www.cppblog.com/mymsdn/archive/2009/10/28/quicksort20091028.html
@你好!
已删除!
孤陋寡闻了,原来这种东西满大街都是,呵呵:
http://blog.sina.com.cn/s/blog_455b20c10100929m.html
http://andylin02.javaeye.com/blog/437166
关键字:字符串相似度,最大公共字符串,LCS算法等
re: QuickSort快速排序法 volnet 2009-06-19 00:10
@bug
非常感谢发现了问题。
能否详细说一下哪里的问题
你的测试数据是多少?我也测测
re: static in C volnet 2009-05-28 04:29
@A
没错,记录一下,嗯,这样以后可以不用翻书也可以找到
@volnet
简单地说,就是修改对应警告项目的属性,并修改编译器类型为Linux GCC即可。
现在出现了一个问题,再Windows下我用Eclipse,Workspace设置再E:\MyCProject中,在Linux下,我同样期待将Eclipse的Workspace设置到相同的路径,于是有\media\Personal\MyCProject,其中Personal是E盘的名称。
这些都没问题,但是在编译的时候出现了问题:
Description Resource Path Location Type
Invalid project path: Include path not found (/media/Personal/MyCProject/cpp_cake_sort/D::/GNU/MinGW/include). cpp_cake_sort pathentry Path Entry Problem
re: Install Linux Fedora 10 volnet 2009-05-10 14:30
终于可以用上Mplayer了,也可以用上Rhythmbox播放器了,但是音质有点糟糕,原因待查。
首先要感谢软件仓库计划,因为简单地使用./configure,make,make install在我的机器上总是会有若干地错误,这些错误涉及到了软件的源码,绝对不是吃干饭的。偶尔发现了上一条留言中所提到的方法。恩,软件仓库,rpm repository!这绝对是一项伟大而有意义的工程,它极大地方便了用户的使用。要使用软件仓库,也就是说你要用yum来安装它,你可能需要先将软件仓库指定成yum的源。
rpm -ivh http://download1.rpmfusion.org/free/fedora/rpmfusion-free-release-stable.noarch.rpm
rpm -ivh http://download1.rpmfusion.org/nonfree/fedora/rpmfusion-nonfree-release-stable.noarch.rpm
这两句话就是干这个用的。
当然在文档中有一种同时使用两者的另一种方式,上面的这种方式再文档中是通过GUI进行安装的,也就是你现在看到两个链接,然后直接在FireFox中点击安装即可。而下面的方式是命令行方式的。意思是一样。参考配置信息(http://rpmfusion.org/Configuration)中的“Command Line Setup using rpm”部分章节(很简单,就几行,找到你的软件版本,比如Fedora 10的发行版)。

下面看下Rhythmbox播放器为什么昨天不行,今天可以?
首先它一直都可以打开,但是对于播放MP3无能为力,因为它通常会在你的Fedora10发行版中自带。而MP3要求交版税的,也就是免费的 Fedora10无法为您提供的软件,但是RPMFusion的出现就是为了解决Fedora project无法免费为您提供的这些涉及版税或者那些源码型的软件分发。
原来你试图打开一个MP3,则会出现一个MPEG-1 编码的问题,但是出现的自动下载插件的对话框并没有办法正确找到这个编码器,取而代之的是它会重定向到某个官方文档告诉你,这个插件可能受法律保护,无法提供给你使用。因此你必须自己手动去搞这些。但是现在你安装(设置)了软件仓库,你的系统将为你找到合适的编码器,并通过yum进行下载。经过一阵的下载后,您的软件就可以用了。很不错。

为什么我喜欢Rhythmbox呢?
因为我一开始看到Rhythmbox的时候就觉得它很像Apple iTunes,管理音乐很好看。而MPlayer我刚刚也见到了,但是它更像一个90年代的播放器,恩,可能皮肤上我需要重设。先用Rhythmbox播吧,呵呵。不过音质确实问题很严重,我的扬声器现在只有1块钱喇叭的效果了。呵呵~


如何下载安装MPlayer呢?

http://hi.baidu.com/ppks/blog/item/8641e8dc47a9b4a9cc116649.html

Fedora不给大家提供带有版权问题或是封源的软件,这个给我们下载软件带来了许多麻烦,所以在这里提供RPM Fusion源,来补充我们Linux的“软件库”。

直接复制到虚拟终端里就好了,必须需要root的权限哦。另外建议直接复制输入,以免打错字。

rpm -ivh http://download1.rpmfusion.org/free/fedora/rpmfusion-free-release-stable.noarch.rpm
rpm -ivh http://download1.rpmfusion.org/nonfree/fedora/rpmfusion-nonfree-release-stable.noarch.rpm

如果安装这个源后还是不能正常使用yum,那很可能是由于key引起,解决办法是在终端里输入下面的代码试试:

Linux下的播放器很丰富,听说最好的还是MPlayer,简单的只要要安装好几个包,现在与大家一起学下一种在Fedora 10安装MPlayer的简便方法。

安装步骤如下:

首先确保你的电脑一定要联网 ,因为是在线安装;

其次打开终端,复制以下代码,回车看看吧

yum install mplayer

yum install mplayer-gui

re: Install Linux Fedora 10 volnet 2009-05-10 12:57
About bz2 & gz files

*.tar.bz2以及*.tar.gz,虽然Linux并不指定后缀名,但从Windows用户的使用习惯以及人类可识别的角度考虑,这样一种命名规则给人更好的理解。当然tar程序并不通过所谓的“后缀”来识别。
现在我们只讨论实际类型与所谓的“后缀”匹配的情况。
gz是指在tar打包的时候指定了用gzip的方式进行压缩,指令是z,也就是说tar -z ****file代表的是使用gzip方式进行压缩。
而bz2则使用了另外一种压缩方式bzip2的方式进行压缩,对应的指令为j。
这一点我们可以通过在命令行输入
man tar | more
进行查看。
因此正如我们在Windows中一样,*.zip与*.rar一样具有不同的压缩格式。
re: Install Linux Fedora 10 volnet 2009-05-10 00:34
映像密码和用户权限

Linux 用户管理的特点之一在于它沿袭了 UNIX 风格,使用 passwd 文件。登录的用户必须可以读取 /etc/passwd 文件,以判断他的用户名是否存在。如果将用户名和密码存放在同一个文件中,潜在的攻击者就可能获得密码;他们可以下载 /etc/passwd 文件,然后以暴力破解的方法获得密码。映像文件不必所有人都可读,这样攻击者将不能获得任何形式的密码。

这种方法还是不最好的,因为攻击还是可以得到 一些 用户信息。更好的方法是将用户保存于一个单独的地方,比如使用 LDAP。
re: Install Linux Fedora 10 volnet 2009-05-09 23:35
关于Webmin

Webmin 是一个用 Perl 编写的基于浏览器的管理应用程序。Webmin 是可扩展的,除了用于 Linux 之外,还可以用于其他类 Unix 操作系统。安装完成后,可以在本地或者远程浏览器通过一个特定的端口,通常是 10000,来进入 Webmin。它具有可以指向和点击的界面,可以完成各种 Linux 管理任务,包括用户管理、网络防火墙和网络设备的配置。

Webmin 安装和使用都是免费的,它是一个很好的管理 Linux 环境的工具,如果您以前用的是 Windows 的图形化管理工具。Webmin 工具是基于控制台的工具的前端,因此使用这两种工具进行配置效果是一致的,它们都可以可靠地完成管理任务。

更多内容:http://www.ibm.com/developerworks/cn/linux/l-roadmap/part3/index.html
re: Install Linux Fedora 10 volnet 2009-05-09 12:50
另外,有个不错地资源推荐给大家:
http://www.ibm.com/developerworks/cn/linux/newto/index.html
新手多看看咯,恩,我现在要开始看了。然后把遇到的问题逐一解决掉
re: C++ notes (1) volnet 2009-03-13 19:15
@sinor51
可以说“不应该”,不能一般是指编译会出错吧
re: 关于http://wap.baidu.com招唤 volnet 2009-03-06 03:11
哈,为什么百度不公布Hi群,要公布QQ群,郁闷~
有什么搜索方面的从入门一直到精通(不是那种书名就这么暴露)的经典著作推荐一下,另外,国内有什么相关资源呢,……你知道我要说什么,不知道,百度一下,呵呵~(开个玩笑)
re: QuickSort快速排序法 volnet 2009-03-06 03:08
如果大家是要写C语言版本呢,我看看:
1、把class包裹的一大堆都去掉(里面的声明可以拷贝出来)
2、把template <typename T>都去掉,Algorithms::也去掉
然后就是调用的地方了,大家自己写一下调用就可以了
@maosher
怎么了?
@Dancefire
谢谢你对Boost做了详细的介绍。
那么,学习Boost库需要有哪些准备工作?(假设从初学者开始)学习Boost库又有哪些方法或者经典的做法呢?(比如什么书,或者什么文档)
@Dancefire
boost在C++中的地位是什么呢?一个工业库?一个泛型标准?一个开源范例?它对C++学习有什么好处呢?
@Dancefire
原来你们说的是include foo.cpp

分开有一个好处就是可以成套地替换吧,虽然通常我们不这么做,但是却从语法上支持了这么做。如果可以当然好了,不行的话肯定是没办法的。
@空明流转
我说的可以是指在h中声明,在cpp中定义,这显然是可以的(也是标准的做法)
模板函数和模板类的确都存在如本文所述的问题,并且用Dancefire的方法,或者使用全部写在.h文件中的方式,都是可以的。
@Dancefire
的确,把foo.cpp移出项目外的话就可以顺利编译并执行了!
但是在你的回答中,为什么会提到“当继续编译main.cpp的时候……”,这是为什么呢?为什么非模板类型就可以?
re: C++ notes (4) volnet 2009-02-06 15:01
@路人丁
----------------------------
const char *cstr = st1.c_str();
std::cout<<cstr<<std::endl;
而不是
std::cout << st1.c_str() << std::endl;

----------------------------
这么写当然不是为了输出,只是为了说明c_str的功能,输出何必这样写呢?

re: C++ notes (3) volnet 2008-12-26 16:00
@飘飘白云
你说的在理,这句话是Lippman说的,话说他们都是大牛,现在看相信谁的了……
这可能涉及到不同的标准库实现方式,看来这个问题要么应该忽略掉,根据实际需求,可以加的就加,不可以加的就算了。
希望有达人来解释一下
re: C++ notes (3) volnet 2008-12-26 00:03
@夜弓
其实不论是哪种类型,自己用习惯了就可以,另外一种,大致了解,以便不会在别人的代码中晕菜即可……
单行的确可以解决这个问题,恩,不过在变量一多的时候,我们可能更经常用多行,事实上,这个也是习惯问题。而且单行可以更好的地注释变量,而多行则通常适用于同一注释的多个变量声明
共2页: 1 2 
特殊功能