2010-05-29 4 views
8

Lors de la lecture de la documentation here, je suis tombé sur ceci:OU des constantes Bitwise

unsigned unitFlags = NSYearCalendarUnit | NSMonthCalendarUnit | NSDayCalendarUnit; 

Je ne sais pas comment cela fonctionne. J'ai lu sur les opérateurs bit à bit en C, mais je ne comprends pas comment vous pouvez tenir trois constantes (ou plus!) Dans un int et plus tard être en mesure de les extraire d'une façon ou d'une autre de l'int? Creuser plus bas la documentation, j'ai aussi trouvé ce qui est probablement lié:

typedef enum { 
    kCFCalendarUnitEra = (1 << 1), 
    kCFCalendarUnitYear = (1 << 2), 
    kCFCalendarUnitMonth = (1 << 3), 
    kCFCalendarUnitDay = (1 << 4), 
    kCFCalendarUnitHour = (1 << 5), 
    kCFCalendarUnitMinute = (1 << 6), 
    kCFCalendarUnitSecond = (1 << 7), 
    kCFCalendarUnitWeek = (1 << 8), 
    kCFCalendarUnitWeekday = (1 << 9), 
    kCFCalendarUnitWeekdayOrdinal = (1 << 10), 
} CFCalendarUnit; 

Comment les états (1 << 3)/variables travail? Je suis désolé si c'est trivial, mais quelqu'un pourrait m'éclairer en expliquant ou peut-être poster un lien vers une bonne explication?

+0

Cela ressemble à l'objectif-c? Est-ce que c'est mal étiqueté? – SoapBox

+0

@SoapBox: L'exemple est en effet tiré de Cocoa, mais il est vraiment droit C. – ryyst

+0

Cette deuxième ligne de code n'est pas C, pas de loin. – SoapBox

Répondre

9

Fondamentalement , les constantes sont représentées par un seul bit, donc si vous avez un entier de 32 bits, vous pouvez y insérer 32 constantes. Vos constantes doivent être des puissances de deux, donc elles ne prennent qu'un seul bit "set" à représenter.

Par exemple:

#define CONSTANT_1 0x01 // 0001 in binary 
#define CONSTANT_2 0x02 // 0010 in binary 
#define CONSTANT_3 0x04 // 0100 in binary 

alors vous pouvez le faire

int options = CONSTANT_1 | CONSTANT_3; // will have 0101 in binary. 

Comme vous pouvez le voir, chaque bit représente cette constante particulière. Ainsi, vous pouvez binaire et dans votre code et vérifier la présence de chaque constante, comme:

if (options & CONSTANT_3) 
{ 
    // CONSTANT_3 is set 
} 

Je vous recommande de lire sur les opérations binaires (ils fonctionnent comme des opérateurs LOGIQUES, mais au niveau du bit), si vous grok ce truc, il va te rendre un peu meilleur d'un programmeur.

Cheers.

1

Le numéro 1 est représenté comme 00000000000000000000000000000001 (1 < < n) signifie déplacer les 1 dans la représentation de 1 n endroits à la gauche So (1 < < 3) serait 00000000000000000000000000001000 Dans un entier, vous pouvez avoir 32 options chacun d'entre eux peut être activé ou désactivé. Numéro d'option n est si le bit est 1 n'th

2

Si vous regardez un nombre en binaire, chaque chiffre est soit (1) ou désactiver (0).

Vous pouvez utiliser des opérateurs au niveau du bit pour définir ou interroger les bits individuels de manière efficace pour voir s'ils sont définis ou non. Prenez la valeur 8 bits 156. En binaire, 10011100.

Les bits positionnés correspondent à des bits 7, 4, 3 et 2 (valeurs 128, 16, 8, 4). Vous pouvez calculer ces valeurs avec 1 << (position) plutôt facilement. Ainsi, 1 << 7 = 128.

0

1 << y est essentiellement la même chose que 2 to the power of y

Plus généralement, x << y est la même chose que x multiplied by 2 to the power of y.

En x << y binaires moyens de déplacement tous les bits de x à gauche par y endroits, en ajoutant des zéros à la place des bits déplacés:

00010 << 2 = 01000

Alors:

1 << 1 = 2 
1 << 2 = 4 
1 << 3 = 8 
... 
0

<< est l'opérateur de décalage vers la gauche, il décale les bits du premier opérande laissé par le nombre de positions spécifiées dans l'opérande de droite (avec des zéros venant des positions décalées par la droite).

Dans votre énumération, vous obtenez des valeurs qui ont un bit différent défini sur 1, donc lorsque vous construisez quelque chose comme unitDate, vous pouvez trouver plus tard quels indicateurs il contient en utilisant l'opérateur &, par ex. unitDate & NSMonthCalendarUnit == NSMonthCalendarUnit sera vrai.

Questions connexes