NSData的转换为基本变量与IEEE-754或二进制补码? [英] Convert NSData to primitive variable with ieee-754 or twos-complement?

查看:158
本文介绍了NSData的转换为基本变量与IEEE-754或二进制补码?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在的OBJ-C 可可新的程序员。我是一个试图写将用于读取二进制文件的框架(灵活的图像传输系统 FITS 二进制文件,通常是由天文学家使用)。二进制数据,我感兴趣提取,可以有不同的格式和我通过阅读的头FITS 文件中获取其属性。

I am new programmer in Obj-C and cocoa. Im a trying to write a framework which will be used to read a binary files (Flexible Image Transport System or FITS binary files, usually used by astronomers). The binary data, that I am interested to extract, can have various formats and I get its properties by reading the header of the FITS file.

到现在为止,我设法创建一个类来存储在的内容符合文件和头隔离到一个的NSString 对象和二进制数据转换成的NSData 对象。我也设法写方法,它让我从中提取标题是国米preT二进制数据非常有价值的核心价值观。

Up to now, I manage to create a class to store the content of the FITS file and to isolate the header into a NSString object and the binary data into a NSData object. I also manage to write method which allow me to extract the key values from the header that are very valuable to interpret the binary data.

现在我想在的NSData 对象转换为基本类型数组的(数组双 INT ...)。但是,在这里,我被卡住,并会AP preciate任何帮助。

I am now trying to convert the NSData object into a primitive array (array of double, int, short ...). But, here, I get stuck and would appreciate any help.

据我对 FITS 文件,我有PT取决于价值的二进制数据5的可能性,除$ P $的 BITPIX 键:

According to the documentation I have about the FITS file, I have 5 possibilities to interpret the binary data depending on the value of the BITPIX key:

BITPIX value | Data represented
  8          | Char or unsigned binary int
 16          | 16-bit two's complement binary integer
 32          | 32-bit two's complement binary integer
 64          | 64-bit two's complement binary integer
-32          | IEEE single precision floating-point
-64          | IEEE double precision floating-point

我已经写code的和平,表明波纹管,要尽量在的NSData 转换为原始数组。

// self reefer to my FITS class which contain a NSString object  
// with the content of the header and a NSData object with the binary data. 

-(void*) GetArray
{
switch (BITPIX)
{
    case 8:
        return [self GetArrayOfUInt];
        break;
    case 16:
        return [self GetArrayOfInt];
        break;
    case 32:
        return [self GetArrayOfLongInt];
        break;
    case 64:
        return [self GetArrayOfLongLong];
        break;
    case -32:
        return [self GetArrayOfFloat];
        break;
    case -64:
        return [self GetArrayOfDouble];
        break;
    default:
        return NULL;
}
}

// then I show you the method to convert the NSData into a primitive array.
// I restrict my example to the case of 'double'. Code is similar for other methods
// just change double by 'unsigned int' (BITPIX 8), 'short' (BITPIX 16)
// 'int' (BITPIX 32) 'long lon' (BITPIX 64), 'float' (BITPIX -32). 

-(double*) GetArrayOfDouble
{
int Nelements=[self NPIXEL]; // Metod to extract, from the header 
                             // the number of element into the array
NSLog(@"TOTAL NUMBER OF ELEMENTS [%i]\n",Nelements);

//CREATE THE ARRAY
double (*array)[Nelements];

// Get the total number of bits in the binary data
int Nbit = abs(BITPIX)*GCOUNT*(PCOUNT + Nelements); // GCOUNT and PCOUNT are defined
                                                        // into the header
NSLog(@"TOTAL NUMBER OF BIT [%i]\n",Nbit);
int i=0;

    //FILL THE ARRAY
double Value;

for(int bit=0; bit < Nbit; bit+=sizeof(double))
{
    [Img getBytes:&Value range:NSMakeRange(bit,sizeof(double))];
    NSLog(@"[%i]:(%u)%.8G\n",i,bit,Value);
        (*array)[i]=Value;
    i++;

}

return (*array);

}

不过,我在打印循环的价值从预期值非常不同的(用比较正式的FITS软件)。因此,我认为在的OBJ-C 双击不使用 IEEE-754 约定还有< STRONG>的OBJ-C INT 不是的补码的。我真的不熟悉这个两公约( IEEE 补码的),并想知道我该怎么做这种转换是的OBJ-C

However, the value I print in the loop are very different from the expected values (compared using official FITS software). Therefore, I think that the Obj-C double does not use the IEEE-754 convention as well as the Obj-C int are not twos-complement. I am really not familiar with this two convention (IEEE and twos-complement) and would like to know how I can do this conversion with Obj-C.

在提前许多感谢任何帮助或信息。

In advance many thanks for any help or information.

推荐答案

非常感谢。这个问题真的涉及到endian和我没有意识到这一点。说实话,我从来没有真正意识到尾数类型的,因为到现在为止,我从来没有遇到这个问题。

Thanks a lot. The problem was really related to the endian and I was not aware of this. Honestly, I was never really aware of the endian type because, up to now, I was never confronted to the problem.

顺便说一句,我找到解决方案,感谢所有为你的话。因为它可以为其他开发人员有用,我会建议code的和平成为可能,这样的NSData转换为原始的,什么都尾数类型。这是我觉得(与基金会和可可框架在OS X 10.5和10.6的工作)的解决方案,它可能不是最好的,所以,需要您自担风险使用;)

By the way, I find the solution, thanks all for your remarks. Because it can be useful for other developer, I will propose a peace of code which allow to convert NSData to primitive, what ever the endian type. This is the solution I find (work with the Foundation and cocoa framework on Os X 10.5 and 10.6) and it may not be the best, so, use at your own risk ;)

// 1- CREATE AN ARRAY OF SIZE Nelements;
int Nelements = XXX;
double (*array)[Nelements];

// 2- Create the swapped double -> a double with the wrong bit order
NSSwappedDouble swappedValue;

// 3- The correct value
double Value;

// 4- Fill your array
int i=0, bit=0;
int BitStep=sizeof(double);

while(i<Nelements)
{
    [MyNSData getBytes:&swappedValue range:NSMakeRange(bit,step)];
    Value = NSSwapBigDoubleToHost(swappedValue);   // or NSSwapLittleDoubleToHost depending of your endian type.
    (*array)[i]=Value;
    i++; bit+=BitStep;

}

希望这是有用的。

Hope this can be useful.

这篇关于NSData的转换为基本变量与IEEE-754或二进制补码?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆