-(UInt8 *)readDcmPixel:(NSString *)dcmFileName{
UInt8 *pixData = NULL;
DicomImage *image = new DicomImage([dcmFileName UTF8String])
;
if (image != NULL) {
if (image->getStatus() == EIS_Normal) {
if (image->isMonochrome()) {
image->setMinMaxWindow();
pixData = (UInt8 *)image->getOutputData(8);
}
}
}
delete image ;
return pixData;
}
在模拟器中,内存会因为delte语句而释放;在真机中却不能释放,而且pixData内容为空了。
原因:真机中使用arc机制,pixData = (UInt8 *)image->getOutputData(8);
其实是pixData指向了(UInt8 *)image->getOutputData(8)的内存地址,然后image的retainCount
+1 , 最后的delete语句就释放不了image的内存了,但是却删除了内存中的内容。
但是模拟器中却好用,猜想是:因为这段代码在.mm文件中,可能台式机(模拟器)的编辑器采用了c++的编译方式,就直接delete了image,但是pixData为什么还有内容呢?搞不懂
为了满足真机,将上面代码改为:
-(UInt8 *)readDcmPixel:(NSString *)dcmFileName size:(int)size{
UInt8 *pixData = NULL;
unsigned char tmp[size] ;
pixData = tmp ;
DicomImage *image = new DicomImage([dcmFileName UTF8String])
;
if (image != NULL) {
if (image->getStatus() == EIS_Normal) {
if (image->isMonochrome()) {
image->setMinMaxWindow();
memcpy(pidData, (UInt8 *)image->getOutputData(8), size);
}
}
}
delete image ;
return pixData;
}
虽然消耗内存问题解决了,但是又带来了以个新问题:外部调用改方法的时候,方法返回的结果数据不完全准确。
原因:改方法返回指针,外部接收返回值的时候确实能正确的接受到指针的首地址,但是那块地址中的内容是否变化了就不能确定了。因为pixData是在方法里面定义的,属于局部变量。当该方法调用结束后,局部变量就要释放了,别的变量就可以用这块地址了,所以导致方法返回数据不完全准确的问题。
最后将方法改为:
-(void)readDcmPixel:(NSString *)dcmFileName size:(int)size
buff:(unsigned char *)buff{
DicomImage *image = new DicomImage([dcmFileName UTF8String])
;
if (image != NULL) {
if (image->getStatus() == EIS_Normal) {
if (image->isMonochrome()) {
image->setMinMaxWindow();
memcpy(buff, (UInt8 *)image->getOutputData(8),
size);
}
}
}
#warning delete image 必须有,否则多次使用该方法会导致内存耗尽
delete image ;
}