Objective-C impliciete conversie verliest integer precisie ‘NSUInteger’ (ook bekend als ‘unsigned long’) naar ‘int’ waarschuwing

Ik ben bezig met een aantal oefeningen en heb een waarschuwing gekregen waarin staat:

Impliciete conversie verliest precisie van gehele getallen: ‘NSUInteger’ (ook bekend als ‘unsigned long’) naar ‘int’

#import <Foundation/Foundation.h>
int main (int argc, const char * argv[])
{
    @autoreleasepool {
        NSArray *myColors;
        int i;
        int count;
        myColors = @[@"Red", @"Green", @"Blue", @"Yellow"];
        count = myColors.count; //  <<< issue warning here
        for (i = 0; i < count; i++)
        NSLog (@"Element %i = %@", i, [myColors objectAtIndex: i]);
    }
    return 0;
}


Antwoord 1, autoriteit 100%

De countmethode van NSArrayretourneert een NSUInteger, en op het 64-bit OS X-platform

  • NSUIntegeris gedefinieerd als unsigned long, en
  • unsigned longis een 64-bits geheel getal zonder teken.
  • intis een 32-bits geheel getal.

Dus intis een “kleiner” datatype dan NSUInteger, vandaar de compilerwaarschuwing.

Zie ook NSUIntegerin de “Foundation Data Types Reference”:

Bij het bouwen van 32-bits toepassingen is NSUInteger een 32-bits niet-ondertekende
geheel getal. Een 64-bits toepassing behandelt NSUInteger als een 64-bits niet-ondertekende
geheel getal.

Om die compilerwaarschuwing op te lossen, kunt u de lokale variabele countdeclareren als

NSUInteger count;

of (als u zeker weet dat uw array nooit meer dan 2^31-1elementen zal bevatten!),
voeg een expliciete cast toe:

int count = (int)[myColors count];

Antwoord 2, autoriteit 5%

In tegenstelling tot Martins antwoord, is casten naar int (of het negeren van de waarschuwing) niet altijd veilig, zelfs als je weet dat je array niet meer dan 2^31-1 elementen bevat. Niet bij het compileren voor 64-bits.

Bijvoorbeeld:

NSArray *array = @[@"a", @"b", @"c"];
int i = (int) [array indexOfObject:@"d"];
// indexOfObject returned NSNotFound, which is NSIntegerMax, which is LONG_MAX in 64 bit.
// We cast this to int and got -1.
// But -1 != NSNotFound. Trouble ahead!
if (i == NSNotFound) {
    // thought we'd get here, but we don't
    NSLog(@"it's not here");
}
else {
    // this is what actually happens
    NSLog(@"it's here: %d", i);
    // **** crash horribly ****
    NSLog(@"the object is %@", array[i]);
}

Antwoord 3

Wijzig sleutel in Project > Build-instelling
typecheck-aanroepen naar printf/scanf: NEE

Uitleg:[Hoe het werkt]

Controleer aanroepen naar printf en scanf, enz., om er zeker van te zijn dat de opgegeven argumenten typen hebben die passen bij de opgegeven formaattekenreeks, en dat de conversies die in de formaattekenreeks zijn gespecificeerd, zinvol zijn.

Hoop dat het werkt

Andere waarschuwing

impliciete conversie van objectief c verliest precisie ‘NSUInteger’ (ook bekend als ‘unsigned long’) naar ‘int

Wijzig sleutel “impliciete conversie naar 32Bits Type > Debug > *64 architectuur: Nee

[let op:Het kan andere waarschuwingen voor 64-bits architectuurconversie ongeldig maken].


Antwoord 4

Het expicit casten naar de “int” lost het probleem in mijn geval op. Ik had hetzelfde probleem. Dus:

int count = (int)[myColors count];

Other episodes