Welcome to ShenZhenJia Knowledge Sharing Community for programmer and developer-Open, Learning and Share
menu search
person
Welcome To Ask or Share your Answers For Others

Categories

I am trying to convert a nsstring with hex values into a float value.

NSString *hexString = @"3f9d70a4";

The float value should be = 1.230.

Some ways I have tried to solve this are:

1.NSScanner

-(unsigned int)strfloatvalue:(NSString *)str
{
   float outVal;
   NSString *newStr = [NSString stringWithFormat:@"0x%@",str];
   NSScanner* scanner = [NSScanner scannerWithString:newStr];
   NSLog(@"string %@",newStr);
   bool test = [scanner scanHexFloat:&outVal];
   NSLog(@"scanner result %d = %a (or %f)",test,outVal,outVal);
   return outVal;
}

results:

 string 0x3f9d70a4
 scanner result 1 = 0x1.fceb86p+29 (or 1067282624.000000)

2.casting pointers

NSNumber * xPtr = [NSNumber numberWithFloat:[(NSNumber *)@"3f9d70a4" floatValue]];

result:3.000000

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
thumb_up_alt 0 like thumb_down_alt 0 dislike
173 views
Welcome To Ask or Share your Answers For Others

1 Answer

What you have is not a "hexadecimal float", as is produced by the %a string format and scanned by scanHexFloat: but the hexadecimal representation of a 32-bit floating-point value - i.e. the actual bits.

To convert this back to a float in C requires messing with the type system - to give you access to the bytes that make up a floating-point value. You can do this with a union:

typedef union { float f; uint32_t i; } FloatInt;

This type is similar to a struct but the fields are overlaid on top of each other. You should understand that doing this kind of manipulation requires you understand the storage formats, are aware of endian order, etc. Do not do this lightly.

Now you have the above type you can scan a hexadecimal integer and interpret the resultant bytes as a floating-point number:

FloatInt fl;
NSScanner *scanner = [NSScanner scannerWithString:@"3f9d70a4"];

if([scanner scanHexInt:&fl.i])        // scan into the i field
{
    NSLog(@"%x -> %f", fl.i, fl.f);   // display the f field, interpreting the bytes of i as a float
}
else
{
    // parse error
}

This works, but again consider carefully what you are doing.

HTH


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
thumb_up_alt 0 like thumb_down_alt 0 dislike
Welcome to ShenZhenJia Knowledge Sharing Community for programmer and developer-Open, Learning and Share
...