2010-03-21 10 views
7

मैं ओबीजेसी में सी structs का उपयोग कर रहा हूं और मैंने एक ऐसा फ़ंक्शन बनाया है जो संरचना को कोको एपीआई से इकट्ठा करता है। चीजें यह है कि यह संरचना NSRect o NSPoint की तरह नहीं है, यह संरचना objc ऑब्जेक्ट्स पैक करती है इसलिए मैं यहां एक संभावित मेमोरी लीक देख रहा हूं। क्या मुझे संरचना को 'रिलीज' करने के लिए एक समारोह प्रदान करने की ज़रूरत है?सी स्ट्रक्चर का उपयोग जिसमें ओबीजेसी ऑब्जेक्ट्स शामिल हैं?

मैं एक ISKNewsCategory कक्षा नहीं बना रहा क्योंकि कोई व्यवहार नहीं होगा लेकिन क्या आपको लगता है कि यह एक अच्छा दृष्टिकोण है या मुझे कक्षा को परिभाषित करना चाहिए, यहां तक ​​कि कोई व्यवहार नहीं होगा?

typedef struct ISK_NewsCategory { 
    NSString *name; 
    NSString *code 
} ISKNewsCategory; 

NS_INLINE ISKNewsCategory ISKMakeNewsCategory(NSString *name, NSString *code) { 
    ISKNewsCategory category; 
    category.name = [name retain]; 
    category.code = [code retain]; 
    return category; 
} 

उत्तर

8

सामान्य रूप से आप एक साधारण कंटेनर कक्षा बनाने से बेहतर होंगे। इस तरह सभी मेमोरी प्रबंधन आसान है और आप NSValue या जो भी हो, में स्ट्रिप को लपेटने के बिना मानक कोको कंटेनर कक्षाओं में ऑब्जेक्ट का उपयोग करने में सक्षम हैं।

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

@interface ISKNewsCategory : NSObject 
{ 
    NSString *name; 
    NSString *code; 
} 
@property (copy) NSString *name; 
@property (copy) NSString *code; 
@end 

@implementation ISKNewsCategory 
@synthesize name,code; 
- (void)dealloc 
{ 
    self.name = nil; 
    self.code = nil; 
    [super dealloc]; 
} 
@end 
+1

अपने "केवल समय" का विस्तार करने के लिए: पुनरावृत्त वर्गों की तुलना में पुनरावृत्त structs 2-4x तेज है। जैसे-जैसे परियोजनाएं बड़ी हो जाती हैं, यह एक वास्तविक समस्या बन रही है (वर्तमान परियोजना कई बार सैकड़ों हजारों वस्तुओं को फिर से शुरू कर रही है, वास्तविक समय में चलनी है)। – Adam

2

जो कुछ भी आप बनाए रखते हैं उसे रिलीज़ करना होगा। हालांकि, ऐसा कुछ भी नहीं है जो कहता है कि आपको उन्हें बनाए रखना होगा। यदि संरचना वस्तुओं का "स्वामित्व" है, तो हाँ, आपको उन्हें बनाए रखना चाहिए, और फिर आपको उन्हें छोड़ना होगा। यदि ऑब्जेक्ट्स कहीं और बनाए रखा जाता है, हालांकि, आप कमजोर संदर्भों पर विचार करना चाहेंगे जहां आप ऑब्जेक्ट्स को बरकरार नहीं रखते हैं।

2

मुझे कक्षाओं को कोई व्यवहार नहीं करने से नफरत है। :/यह उद्देश्य-सी का एक दुखद पहलू है: कक्षाएं वर्बोज़ हैं।

आपको याद रखना होगा कि सी में संरचनाएं हर बार पारित होने पर प्रतिलिपि बनाई जाती हैं। इसलिए, यदि आपकी संरचनाएं अपनी वस्तुओं को बरकरार रखती हैं और आप उन्हें किसी और को देते हैं, तो आप स्वचालित रूप से वस्तुओं के लिए एक गलत संदर्भ गणना के साथ समाप्त हो जाते हैं।

यदि आप अपनी वस्तुओं के चारों ओर गुजरने की योजना बना रहे हैं, तो मुझे लगता है कि आपको इसे एक पूर्ण श्रेणी बनाना चाहिए। यदि आप नहीं करते हैं, तो एक साधारण संरचना ठीक रहेगी।

"विनाशक" की आवश्यकता के अनुसार, आपके पास एक होना चाहिए। आपकी संरचना के लिए सफाई करने के लिए आपके पास हमेशा एक होना चाहिए।

+0

असल में, प्रतिलिपि किसी ऑब्जेक्ट को सीधे पास करने से कहीं अधिक अतिरिक्त बनाए रखने का कारण नहीं बनती है, क्योंकि केवल पॉइंटर की प्रतिलिपि बनाई जाती है। – cobbal

+0

@ कोबबल: यही मेरा मतलब था। यदि आप अपनी संरचना को चारों ओर पास करते हैं, तो ऑब्जेक्ट्स के पॉइंटर्स की प्रतिलिपि बनाई जाएगी, और यदि आप उन्हें प्रत्येक संरचना के लिए बनाए रखना चाहते हैं, तो आप ऐसा नहीं कर सकते हैं। – zneak

0

मुझे आशा है कि यह समाधान आपके लिए सहायक होगा।

typedef struct ISK_NewsCategory { 
    NSString *name; 
    NSString *code; 
} ISKNewsCategory; 

NS_INLINE ISKNewsCategory ISKMakeNewsCategory(NSString *inName, NSString *inCode) { 

    ISKNewsCategory category; 

    [category.name autorelease]; 
    category.name = [inName retain]; 

    [category.code autorelease]; 
    category.code = [inCode retain]; 

    return category; 
} 
संबंधित मुद्दे