2013-02-13 17 views
5

में एनएसपीडिकेट का उपयोग करके एनएसएमयूटेबलएरे से अलग इकाई ऑब्जेक्ट प्राप्त करें मेरे पास NSMutableArray है जिसमें इकाई वर्ग ऑब्जेक्ट की ऑब्जेक्ट्स है। अब मैं इससे अलग वस्तुओं को हटाना चाहता हूं। उदाहरणआईएसएम एसडीके

Entity *entity = [[Entity alloc] init]; 
entity.iUserId = 1; 
entity.iUserName = @"Giri" 
[arr addObject:entity]; 

Entity *entity = [[Entity alloc] init]; 
entity.iUserId = 2; 
entity.iUserName = @"Sunil" 
[arr addObject:entity]; 

Entity *entity = [[Entity alloc] init]; 
entity.iUserId = 3; 
entity.iUserName = @"Giri" 
[arr addObject:entity]; 

अब मैं डुप्लिकेट iUserName को हटाने के द्वारा Array में केवल दो वस्तुओं चाहते हैं निम्नलिखित पर विचार करें। मैं पुनरावृत्ति के माध्यम से जानता हूं लेकिन मैं इसे predicate या किसी अन्य तरीके से पुन: प्रयास किए बिना चाहता हूं। यदि कोई जानता है तो कृपया मेरी मदद करें। मैंने [arr valueForKeyPath:@"distinctUnionOfObjects.iUsername"]; का उपयोग करने का प्रयास किया था, लेकिन यह मुझे लुप्तप्राय वस्तु वापस नहीं करता है।

यह प्रश्न पहले से पूछे गए प्रश्नों से बिल्कुल अलग है। पहले पूछे जाने वाले प्रश्न अलग-अलग ऑब्जेक्ट्स सही होने के लिए हैं, लेकिन वे लूपिंग & का उपयोग करते हैं, मुझे यह नहीं चाहिए। मैं इसे NSPredicate या किसी भी अन्य साधारण विकल्प से चाहता हूं जो लूपिंग से बचाता है।

+0

"आईफोन एसडीके में" - इसके लिए धन्यवाद! यह लंबे समय से रहा है क्योंकि किसी ने इसे सही तरीके से उपयोग किया है (एक्सकोड "शब्द का उपयोग करके अनुचित के बजाय)। –

+0

मुझे याद है कि मैंने इस तरह के प्रश्न को 3-4 बार हल किया है। तो खोज/गूगल करने के लिए शर्मिंदा महसूस न करें। –

+1

@AKV मैं इकाई वर्ग इकाई वस्तु से इकाई की तुलना करके विशिष्ट तत्व चाहता हूं। इसके अलावा मैं लूप के लिए बचाना चाहता हूँ। क्या यह भविष्यवाणी या किसी अन्य विकल्प के माध्यम से संभव है – Girish

उत्तर

0

ठीक है आपके पास कुछ विकल्प हैं (जिन्हें मैं सोच सकता हूं)।

  1. एनएसएआरएआरई के बजाय एनएसएससेट का उपयोग करें।
  2. लूप के लिए उपयोग करें (लेकिन आप सरणी के माध्यम से पुनरावृत्ति नहीं करना चाहते हैं)
  3. एक अनुमानित खोज iUserName का उपयोग यह देखने के लिए करें कि नाम सरणी में जोड़ने से पहले मौजूद है या नहीं।

कुछ की तरह:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"iUserName == 'Giri'"]; 
NSArray *searchArray = [arr filterUsingPredicate:predicate]; 
4

संपादित: आप आप क्या मैन्युअल सरणी पर पाशन और एक नई सरणी के निर्माण के बिना करना चाहते हैं नहीं कर सकते। नीचे दिया गया जवाब काम नहीं करेगा क्योंकि यह मानता है कि केवल दो डुप्लिकेट हैं।

NSMutableArray *filteredArray = [NSMutableArray array]; 

for (Entity *entity in arr) 
{ 
    BOOL hasDuplicate = [[filteredArray filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"iUserName == %@", entity.iUserName]] count] > 0; 

    if (!hasDuplicate) 
    { 
     [filteredArray addObject:entity]; 
    } 
} 

यह फ़िल्टर किए गए सरणी में डुप्लिकेट की तलाश करेगा क्योंकि यह इसे बनाता है।

मूल उत्तर

शुरू तुम एक NSSet उपयोग नहीं कर सकते क्योंकि Entity उदाहरणों compareTo: में NSOrderedSame वापस जाने के लिए है, जो एक अच्छा विचार नहीं है, क्योंकि आप में अद्वितीय पहचानकर्ता के रूप में नाम का उपयोग नहीं करना चाहिए होगा।

आप भविष्यवाणियों का उपयोग कर सकते हैं, लेकिन वे अभी भी कुछ अनुकूलन के बिना O(n^2) समय में सरणी पर लूप करेंगे।

NSArray *filteredArray = [arr filteredArrayUsingPredicate:[NSPredicate predicateWithBlock:^BOOL(Entity *evaluatedObject, NSDictionary *bindings) { 
    return [[arr filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"iUserName == %@", evaluatedObject.iUserName]] count] > 1; 
}]]; 

यह ठीक काम करेगा। आप पहले iUserName संपत्ति द्वारा सरणी को सॉर्ट करके और सॉर्ट किए गए सरणी पर एक रैखिक स्कैन करके इसे पहले भी तेज बना सकते हैं (जब आप पहली डुप्लिकेट देखते हैं तो रोकना)। यदि आप छोटे नमूना आकार (कहें, दस हजार या उससे कम) के साथ काम कर रहे हैं तो यह बहुत काम है। यह शायद आपके समय के लायक नहीं है, इसलिए उपर्युक्त कोड का उपयोग करें।

+0

मैंने आपके समाधान का प्रयास किया था लेकिन यह काम नहीं करता है। मैंने निम्नलिखित कोड का उपयोग किया NSArray * filteredArray = [arr filteredArrayUsingPredicate: [NSPredicate predicateWithBlock:^BOOL (Entity * entity, NSDictionary * बाइंडिंग्स) { वापसी [[arr filteredArrayUsingPredicate: [NSPredicate predicateWithFormat: @ "iUsername ==% @", व्यायाम .iUsername]] गिनती]> 1; }]]; – Girish

+0

यह काम करना चाहिए, हां। –

+0

मेरी सरणी में से कुल 14 तत्व हैं, 7 आम हैं इसलिए इसे 6 तत्वों को वापस करने की आवश्यकता है लेकिन यह 13 तत्व लौटाता है। – Girish

संबंधित मुद्दे