2012-11-20 170 views
0

我接手一個項目,它使用一個枚舉標誌的API調用。的Objective-C的typedef枚舉 - 兩個枚舉映射到相同的價值觀

它可以通過對枚舉值進行OR運算來過濾它們,所以以前的開發者做了一些移位操作。

typedef enum { 
APICallTimeSeriesSearchTimeSeries = (1LL << 1), 
APICallTimeSeriesGetTimeSeriesInfo = (1LL << 2), 
APICallTimeSeriesGetSeriesInfo  = (1LL << 3), 
.... 
APICallFavouritesAddNewsFavourite    = (1LL << 79), 
APICallFavouritesRemoveNewsFavourite   = (1LL << 80), 
APICallFavouritesGetAllFavourites    = (1LL << 81) 
} APICallType; 

然後我們可以做的事情一樣

filter(APICallTimeSeriesGetTimeSeriesInfo | APICallTimeSeriesGetSeriesInfo | APICallTimeSeriesGetSeriesData); 

但最近我發現映射到相同的值類似枚舉。 我甩了整個枚舉列表,像這樣

NSLog(@"%d",APICallTimeSeriesSearchTimeSeries); 
NSLog(@"%d",APICallTimeSeriesGetTimeSeriesInfo); 
NSLog(@"%d",APICallTimeSeriesGetSeriesInfo); 
NSLog(@"%d",APICallTimeSeriesGetSeriesData); 
NSLog(@"%d",APICallFleetSearchVessels); 
NSLog(@"%d",APICallFleetGetVesselInfo); 
etc. 

,我們可以看到在行動bitshifting

2 
4 
8 
16 
32 
64 
128 
256 
512 
1024 
2048 
4096 
8192 
16384 
32768 
65536 
131072 
262144 
524288 
1048576 
2097152 
4194304 
8388608 
16777216 
33554432 
67108864 
134217728 
268435456 
536870912 
1073741824 
2147483648 
4294967296 
8589934592 
17179869184 
34359738368 
68719476736 

之後(1LL < < 63)所產生的問題,相同的價值觀

1152921504606846976 APICallFavouritesAddMarketFavourite = (1LL << 60) 
2305843009213693952 APICallFavouritesRemoveMarketFavourite = (1LL << 61) 
4611686018427387904 APICallFavouritesGetFutureFavourites = (1LL << 62) 
-9223372036854775808 APICallFavouritesAddFutureFavourite = (1LL << 63) 
-9223372036854775808 APICallFavouritesRemoveFutureFavourite = (1LL << 64) 
-9223372036854775808 APICallFavouritesRemoveVesselFavourite = (1LL << 65) 

etc等值(-9223372036854775808)重複所有新枚舉

從這個線程 Types in objective-c on iPhone

其因爲-9223372036854775808是LLONG_MIN

NSLog(@"LLONG_MIN: %lli", LLONG_MIN); // signed long long int 

我那裏有注意到一個較高的值

NSLog(@"LLONG_MAX: %lli", LLONG_MAX); 
NSLog(@"ULLONG_MAX: %llu", ULLONG_MAX); // unsigned long long int 

LLONG_MIN: -9223372036854775808   
LLONG_MAX: 9223372036854775807   
ULLONG_MAX: 18446744073709551615 

但無法找到ULLONG_MIN

我們如何解決這個問題?

我試圖將原始存儲從1LL更改爲1ULL,但沒有效果。

FROM:

typedef enum { 
APICallTimeSeriesSearchTimeSeries = (1LL << 1), 
APICallTimeSeriesGetTimeSeriesInfo = (1LL << 2), 
APICallTimeSeriesGetSeriesInfo  = (1LL << 3), 
... 

TO:

typedef enum { 
APICallTimeSeriesSearchTimeSeries    = (1ULL << 1), 
APICallTimeSeriesGetTimeSeriesInfo    = (1ULL << 2), 
APICallTimeSeriesGetSeriesInfo     = (1ULL << 3), 
... 

歡呼聲

+1

類型除非你的編譯器支持原生128位整數,你可以未定義大於「UINT64_MAX == 2 ** 64 - 1」的枚舉。 –

+0

因爲您已將位移到了已簽名的long變量末尾以外,所以您獲得了LLONG_MIN,這意味着它全部爲零。將它更改爲無符號不會產生任何影響(它只會將它們更改爲0而不是LLONG_MIN,它不會購買任何內容)。要麼你不得不放棄組合它們的能力,要麼將它們分離成代表不同事物的多個不同的枚舉。 – Kitsune

+0

是的,我選擇了第二條路徑。見下文 。乾杯 –

回答

1

ULLONG_MIN是0 ULLONG裝置無符號長長,即正由64位表示的值。

如果您想要正數和負數,您只能表示您可以用相同位寬度的無符號類型表示的該組值的一半。這是該ULLONG_MAX較大的原因。

0

我選擇將APICallType拆分爲另一個枚舉。這是重新連接或一個3歲多的項目,必須測試每個API調用。

APICallTimeSeriesSearchTimeSeries = (1LL << 1), 
APICallTimeSeriesGetTimeSeriesInfo = (1LL << 2), 
APICallTimeSeriesGetSeriesInfo  = (1LL << 3), 
.... 
APICallFavouritesAddNewsFavourite    = (1LL << 79), 
APICallFavouritesRemoveNewsFavourite   = (1LL << 80), 
APICallFavouritesGetAllFavourites    = (1LL << 81) 
} APICallType; 

改爲

typedef enum { 
APICallTimeSeriesSearchTimeSeries = (1LL << 1), 
APICallTimeSeriesGetTimeSeriesInfo = (1LL << 2), 
APICallTimeSeriesGetSeriesInfo  = (1LL << 3), 
APICallTimeSeriesGetSeriesData  = (1LL << 4), 
APICallFleetSearchVessels   = (1LL << 5), 
APICallFleetGetVesselInfo   = (1LL << 6), 
APICallNewsGetNewsItems    = (1LL << 7), 
APICallNewsGetPublicationItems  = (1LL << 8), 
APICallPodcastGetPodcastItems  = (1LL << 9), 
APICallUserLoginAuthenticateUser = (1LL << 10), 
APICallFFASearchFFARoutes   = (1LL << 11), 
APICallFFAGetRouteData    = (1LL << 12), 
APICallOwnerSearchOwners   = (1LL << 13), 
APICallOwnerGetOwnerFleet   = (1LL << 14), 
APICallIndicesSearchIndices   = (1LL << 15), 
APICallIndicesGetIndicesData  = (1LL << 16), 
APICallEquitiesGetEquitiesData  = (1LL << 17), 
APICallEquitiesGetEquityPreviews = (1LL << 18), 
APICallEquitiesSearchBrokingStocks = (1LL << 19), 
APICallEquitiesSearchIndices  = (1LL << 20), 
APICallEquitiesSearchCurrencies  = (1LL << 21), 
APICallEquitiesGetRelatedNewsItems = (1LL << 22), 
APICallEquitiesGetCurrencyList  = (1LL << 23), 
APICallSandPVesselsSearch   = (1LL << 24), 
APICallSandPVesselSalesSearch  = (1LL << 25), 
APICallSandPGetCommercialData  = (1LL << 26), 
APICallSandPGetSimilarSales   = (1LL << 27), 
APICallSandPGetFullVesselDetails = (1LL << 28), 
APICallSandPEnquiriesSearch   = (1LL << 29), 
APICallTimeSeriesGetCategories     = (1LL << 30), 
APICallTimeSeriesGetShipTypes     = (1LL << 31), 
APICallTimeSeriesGetDataTypes     = (1LL << 32), 
APICallTimeSeriesSearchTimeSeriesWithCategories = (1LL << 33), 
APICallHomeGetComments       = (1LL << 34), 
APICallEquitiesGetRelatedNewsItemsWithIds  = (1LL << 35), 
APICallEquitiesSearchEquitiesBrokingStocks  = (1LL << 36), 
APICallTimeSeriesGetFutureShipTypes    = (1LL << 37), 
APICallTimeSeriesGetFutureDataTypes    = (1LL << 38), 
APICallTimeSeriesGetOHLCData     = (1LL << 39), 
APICallTimeSeriesGetSeriesDataMaxPoints   = (1LL << 40), 
APICallTimeSeriesGetSeriesOHLCDataMaxPoints  = (1LL << 41), 
APICallClientSearchClients      = (1LL << 42), 
APICallClientGetClientListForBroker    = (1LL << 43), 
APICallClientSearchDivisionsAndDesks   = (1LL << 44), 
APICallClientGetDivisionsAndDesks    = (1LL << 45), 
APICallClientSaveEmployeeDetails    = (1LL << 46), 
APICallTimeSeriesSearchWithSeriesId    = (1LL << 47), 
APICallHomeGetCommentsCargo      = (1LL << 48), 
APICallHomeGetCommentsSandP      = (1LL << 49), 
APICallHomeGetCommentsTanker     = (1LL << 50), 
APICallClientGetSandPRoutes      = (1LL << 51), 
APICallClientGetSandP2ndHandValues    = (1LL << 52), 
APICallHomeGetCommentsSpecialised    = (1LL << 53), 
APICallClientGetSpecialised      = (1LL << 54), 
APICallClientGetGas        = (1LL << 55), 
APICallClientGetGasBunkerPrices     = (1LL << 56), 
APICallFFAGetAllWhiteboardSpreadTypes   = (1LL << 57), 
APICallFFAGetWhiteboardSpreadPricesForType  = (1LL << 58), 
APICallFavourites        = (1LL << 59) 
/* 
APICallFavouritesGetMarketFavourites   = (1LL << 59), 
APICallFavouritesAddMarketFavourite    = (1LL << 60), 
APICallFavouritesRemoveMarketFavourite   = (1LL << 61), 
APICallFavouritesGetFutureFavourites   = (1LL << 62), 

//Enum bit shifted greater than 63 will have same value as MAX INT reached 
//moved these to 
APICallFavouritesAddFutureFavourite    = (1LL << 63), 
APICallFavouritesRemoveFutureFavourite   = (1LL << 64), 
APICallFavouritesGetVesselOwnerFavourites  = (1LL << 65), 
APICallFavouritesGetVesselFavourites   = (1LL << 66), 
APICallFavouritesAddVesselFavourite    = (1LL << 67), 
APICallFavouritesRemoveVesselFavourite   = (1LL << 68), 
APICallFavouritesGetOwnerFavourites    = (1LL << 69), 
APICallFavouritesAddOwnerFavourite    = (1LL << 70), 
APICallFavouritesRemoveOwnerFavourite   = (1LL << 71), 
APICallFavouritesGetShippingStockFavourites  = (1LL << 72), 
APICallFavouritesAddShippingStockFavourite  = (1LL << 73), 
APICallFavouritesRemoveShippingStockFavourite = (1LL << 74), 
APICallFavouritesGetIndicieFavourites   = (1LL << 75), 
APICallFavouritesAddIndicieFavourite   = (1LL << 76), 
APICallFavouritesRemoveIndicieFavourite   = (1LL << 77), 
APICallFavouritesGetNewsFavourites    = (1LL << 78), 
APICallFavouritesAddNewsFavourite    = (1LL << 79), 
APICallFavouritesRemoveNewsFavourite   = (1LL << 80), 
APICallFavouritesGetAllFavourites    = (1LL << 81) 
*/ 

} APICallType; 

,並添加APICallSubType

typedef enum { 

/* for use with APICallType:APICallFavourites */ 
APICallFavouritesGetMarketFavourites   = (1LL << 1), 
APICallFavouritesAddMarketFavourite    = (1LL << 2), 
APICallFavouritesRemoveMarketFavourite   = (1LL << 3), 

APICallFavouritesGetFutureFavourites   = (1LL << 4), 
APICallFavouritesAddFutureFavourite    = (1LL << 5), 
APICallFavouritesRemoveFutureFavourite   = (1LL << 6), 

APICallFavouritesGetVesselOwnerFavourites  = (1LL << 7), 
APICallFavouritesGetVesselFavourites   = (1LL << 8), 
APICallFavouritesAddVesselFavourite    = (1LL << 9), 
APICallFavouritesRemoveVesselFavourite   = (1LL << 10), 

APICallFavouritesGetOwnerFavourites    = (1LL << 11), 
APICallFavouritesAddOwnerFavourite    = (1LL << 12), 
APICallFavouritesRemoveOwnerFavourite   = (1LL << 13), 

APICallFavouritesGetShippingStockFavourites  = (1LL << 14), 
APICallFavouritesAddShippingStockFavourite  = (1LL << 15), 
APICallFavouritesRemoveShippingStockFavourite = (1LL << 16), 

APICallFavouritesGetIndicieFavourites   = (1LL << 17), 
APICallFavouritesAddIndicieFavourite   = (1LL << 18), 
APICallFavouritesRemoveIndicieFavourite   = (1LL << 19), 

APICallFavouritesGetNewsFavourites    = (1LL << 20), 
APICallFavouritesAddNewsFavourite    = (1LL << 21), 
APICallFavouritesRemoveNewsFavourite   = (1LL << 22), 
APICallFavouritesGetAllFavourites    = (1LL << 23) 
//do not go over (1LL << 63) - enum values start at MAX INT after that 

} APICallSubType; 

,任何地點我檢查我不得不事後檢查亞型

filter(APICallFavourites); 
filterSubType(APICallFavouritesAddVesselFavourite | 
       APICallFavouritesRemoveVesselFavourite); 

if (responseOfSubType(APICallFavouritesAddVesselFavourite)) 
{ 
    NSLog(@"%s APICallFavouritesAddVesselFavourite response not handled", __PRETTY_FUNCTION__); 
} 

if (responseOfSubType(APICallFavouritesRemoveVesselFavourite)) 
{ 
    NSLog(@"%s APICallFavouritesRemoveVesselFavourite response not handled", __PRETTY_FUNCTION__); 
}