ऑब्जेक्टिव-सी में अशक्त स्ट्रिंग की जांच करने का सही तरीका क्या है?


184

मैं अपने iPhone ऐप में इसका इस्तेमाल कर रहा था

if (title == nil) {
    // do something
}

लेकिन यह कुछ अपवाद फेंकता है, और कंसोल दिखाता है कि शीर्षक "(अशक्त)" है।

इसलिए मैं अभी इसका उपयोग कर रहा हूं:

if (title == nil || [title isKindOfClass:[NSNull class]]) {
    //do something
}

क्या अंतर है, और यह निर्धारित करने का सबसे अच्छा तरीका क्या है कि एक स्ट्रिंग अशक्त है?


जवाबों:


395

जैसा कि अन्य लोगों ने बताया है, कोको / ऑब्जेक्टिव सी के तहत कई प्रकार के "अशक्त" हैं, लेकिन एक और ध्यान देने योग्य बात यह है कि [शीर्षक isKindOfClass: [NSNull class]] व्यर्थ जटिल है क्योंकि [NSNull Cull] एक होने के लिए प्रलेखित है। सिंगलटन ताकि आप केवल सूचक समानता की जांच कर सकें। कोको के लिए विषय देखें : अशक्त का उपयोग करना

तो एक अच्छी परीक्षा हो सकती है:

if (title == (id)[NSNull null] || title.length == 0 ) title = @"Something";

ध्यान दें कि आप इस तथ्य का उपयोग कैसे कर सकते हैं कि भले ही शीर्षक शून्य हो, title.length इस मामले में 0 / nil / false, यानी 0 वापस कर देगा, इसलिए आपको इसे विशेष मामला करने की आवश्यकता नहीं है। यह एक ऐसी चीज है जो उन लोगों के लिए है जो ऑब्जेक्टिव सी के लिए नए हैं, उन्हें इस्तेमाल करने में परेशानी हो रही है, विशेष रूप से अन्य भाषाओं में जहां संदेश / विधि कॉल क्रैश करने के लिए आते हैं।


धन्यवाद! हालाँकि मैंने यह सवाल पहली जगह में पूछा क्योंकि मुझे अपवाद मिल रहा था क्योंकि "शीर्षक" शून्य था।
तेओ च्योंग पिंग

1
शीर्षक किस प्रकार का माना जाता है? यदि यह एक NSString है, उदाहरण के लिए, मुझे निम्नलिखित चेतावनी मिलती है: अलग-अलग उद्देश्य-सी प्रकार की संरचना 'NSNull *' और 'संरचनात्मक NSString *' की तुलना में कलाकारों की कमी होती है, इसे दूर करने का कोई तरीका नहीं है (यदि किसी चीज़ में बदलाव हुआ है, तो मैं इसे समाप्त कर दूंगा) यह सवाल पूछा गया था)?
thebossman

1
यह संकलन के बिना कोड पोस्ट करने के लिए मुझे सही काम करता है; ;-)। शीर्षक संभवतः एक NSString है, लेकिन शीर्षक के प्रकार की परवाह किए बिना, केवल सामान्य आईडी प्रकार के लिए शून्य डाला: (आईडी) [NSNull null]।
पीटर एन लुईस

1
@JLT nil और [NSNull null] कभी एक समान नहीं होंगे। [NSNull null] एक सिंगलटन ऑब्जेक्ट है जिसका उपयोग nil के लिए स्टैंड के रूप में किया जा सकता है जब nil का उपयोग नहीं किया जा सकता है (जैसे NSArray या NSDictionary मूल्य में)। इसलिए एक उपयोग का मामला हो सकता है जहां आपके पास वैकल्पिक तारों का एक NSArray था, जिनमें से कुछ शून्य हो सकते हैं, और आप अशक्त मामलों के लिए सरणी में [NSNull null] का उपयोग करते हैं। व्यवहार में, परीक्षण की शायद ही कभी आवश्यकता होती है, केवल तब जब आप (या आपके द्वारा उपयोग किया जाने वाला पुस्तकालय!) प्लेसहोल्डर के रूप में सक्रिय रूप से [NSNull null] का उपयोग करते हैं।
पीटर एन लुईस

1
स्पंदन से यहां आ रहा है, और इस कारण की तलाश कर रहा है कि किसी Mapवस्तु का मूल्य - जो nullडार्ट में है - के अनुरूप नहीं है nilया NULLउद्देश्य सी में नहीं है। कारण यह था कि यह वास्तव में है NUNull null, NULLअशक्त नहीं । धन्यवाद @PeterNLewis!
अलेक्जेंडर

25

यह उतना ही सरल है जितना कि

if([object length] >0)
{
  // do something
}

याद रखें कि वस्तु C में यदि ऑब्जेक्ट शून्य है तो यह मान के रूप में 0 देता है।

यह आपको एक अशक्त स्ट्रिंग और एक 0 लंबाई स्ट्रिंग दोनों मिलेगा।


49
यदि ऑब्जेक्ट NSNull है, तो यह काम नहीं करेगा, फिर भी पहले स्पष्ट रूप से जांचने की आवश्यकता है।
जेरेमी मैक

6
आप NSNull के लिए एक श्रेणी भी बना सकते हैं ताकि यह 0 संदेश लंबाई में वापस आ जाए :)
मिहाई तिमार

1
हाँ, अगर वस्तु NSNull है तो यह दुर्घटनाग्रस्त हो जाएगी।
11:40 पर माइक गल्डहिल

यदि NSNull के बराबर है तो यह दुर्घटनाग्रस्त हो जाएगा
joan

1
NSNull अपरिचित चयनकर्ता समस्या के अतिरिक्त, यह NSString पॉइंटर के बीच अंतर नहीं करेगा जो nil है, या NSString जो वास्तव में है, लेकिन अनिवार्य रूप से एक खाली स्ट्रिंग है। (उदाहरण के लिए एक शाब्दिक object = @"";या के रूप में object = nil;)
केली.दुप

6

इस साइट पर निम्नलिखित संबंधित लेख देखें:

मुझे लगता है कि आपकी त्रुटि कुछ और से संबंधित है क्योंकि आपको अतिरिक्त जाँच करने की आवश्यकता नहीं होनी चाहिए।

इस संबंधित प्रश्न को भी देखें: nil sqlite टेक्स्ट कॉलम की उचित जाँच


अनायास मेरे पास दूसरा हाइपरलिंक (इस साइट पर भी कुछ करने के लिए) को जोड़ने के लिए पर्याप्त "अंक" नहीं हैं, यह भी देखें: - stackoverflow.com/questions/598396/…
टिमम

...मुझे अनुमति दें। हालाँकि आपको अपने स्वयं के पोस्ट को rep 0. से संपादित करने में सक्षम होना चाहिए
Rog

धन्यवाद - वह बहुत दयालु था। जब मैंने अपनी प्रारंभिक पोस्ट लिखी तो यह कहा कि नए उपयोगकर्ता केवल 1 हाइपरलिंक जोड़ सकते हैं (जो थोड़ा कठोर लगता है - विशेष रूप से इस साइट में क्रॉस लिंक के लिए)।
टिमम

6

मैंने पाया है कि वास्तव में ऐसा करने के लिए आप अंत में कुछ ऐसा ही करने के लिए तैयार हैं

if ( ( ![myString isEqual:[NSNull null]] ) && ( [myString length] != 0 ) ) {
}

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


5

इन सभी के साथ Whats "मेरे जवाब के लिए काम करता है"? हम सभी एक ही भाषा में कोडिंग कर रहे हैं और नियम हैं

  1. सुनिश्चित करें कि संदर्भ शून्य नहीं है
  2. जाँच करें और सुनिश्चित करें कि स्ट्रिंग की लंबाई 0 नहीं है

वही है जो सभी के लिए काम करेगा। यदि कोई दिया गया समाधान केवल "आपके लिए काम करता है", तो इसका केवल यही कारण है कि आपका एप्लिकेशन प्रवाह उस परिदृश्य के लिए अनुमति नहीं देगा जहां संदर्भ शून्य हो सकता है या स्ट्रिंग की लंबाई 0. हो सकती है। ऐसा करने का उचित तरीका वह तरीका है जो संभाल लेगा आप सभी मामलों में क्या चाहते हैं।


4
यदि संदर्भ है nil(नोट: "शून्य" नहीं), तो एक संदेश भेजना, जैसे length, 0 का उत्पादन करेगा (या विधि के वापसी प्रकार के लिए उपयुक्त 0-मान)। यही भाषा का नियम है। nilइस मामले में अलग से जाँच करने की कोई आवश्यकता नहीं है ।
jscs

मैंने कहा कि सी ++ आदतों की वजह से बस अशक्त है, और यदि आपका कोड शून्य वस्तुओं पर कॉल कर रहा है, तो संभावना है कि आपका कोड टूट गया है। आप पाएंगे कि NULL / NIL (एक ही अवधारणा) पर कॉलिंग विधियाँ आमतौर पर किसी भी भाषा में एक बुरा विचार है। सिर्फ इसलिए कि obj-c आपको कुछ ऐसा करने देता है, जिसका मतलब यह नहीं है कि आपको सिर्फ नील वस्तुओं के आसपास से गुजरना चाहिए और उन्हें बिना देखभाल के उपयोग करने की कोशिश करनी चाहिए।
nenchev

1
NIL में लंबाई भेजना 0 का उत्पादन करता है - लेकिन NSNull में लंबाई भेजना एक अपवाद पैदा करता है।
cdstamper

@nenchev कोई भी केवल निल वस्तुओं के आस-पास से गुजरने के बारे में कुछ नहीं कहता है, लेकिन निल के लिए जाँच करना, फिर एक विधि को कॉल करना और इसके रिटर्न मान का उपयोग करना किसी भाषा सुविधा का उपयोग करने की तुलना में आईएमओ से भी बदतर है जैसा कि इसका उपयोग करने के लिए है और बाद में विधि की वापसी की वैधता की जांच करना है।
केविन

@ केविन मुझे यकीन नहीं है कि इसका वास्तव में कितना बुरा है, सिर्फ इसलिए कि इसकी भाषा की विशेषता इसका महान नहीं है। जाँच नहीं कि क्या इसकी अशक्तता एक कोड पथ को खोल सकती है जो रनटाइम त्रुटि का पता लगाने के लिए कठिन हो सकती है। यह आमतौर पर यह सत्यापित करने के लिए सबसे अच्छा है कि आपके इनपुट आपकी अपेक्षा के अनुरूप हैं, और यदि वे नहीं हैं तो तदनुसार प्रतिक्रिया करें। मैं व्यक्तिगत रूप से एक नील वस्तु को संदेश भेजने की कोशिश करते समय रन-टाइम अपवाद नहीं पाने की "सुविधा" को पसंद नहीं करता, क्योंकि यह अक्सर कुछ रनटाइम बग्स को याद रखना आसान बनाता है।
nenchev

4

यदि आप सभी शून्य / खाली वस्तुओं (जैसे खाली तार या खाली सरण / सेट) का परीक्षण करना चाहते हैं, तो आप निम्नलिखित का उपयोग कर सकते हैं:

static inline BOOL IsEmpty(id object) {
    return object == nil
        || ([object respondsToSelector:@selector(length)]
        && [(NSData *) object length] == 0)
        || ([object respondsToSelector:@selector(count)]
        && [(NSArray *) object count] == 0);
}

2
यह वास्तव में ऑब्जेक्ट के लिए जांच नहीं करता है == [NSNull null] जो शायद समझ में आएगा।
पीटर एन लुईस

3

दो स्थितियां हैं:

यह संभव है कि एक वस्तु है [NSNull null], या यह असंभव है।
आपका एप्लिकेशन आमतौर पर [NSNull null];आपको केवल उसी का उपयोग नहीं करना चाहिए यदि आप किसी " नल " ऑब्जेक्ट को किसी सरणी में रखना चाहते हैं , या इसका उपयोग शब्दकोश मान के रूप में करना चाहते हैं। और फिर आपको पता होना चाहिए कि कौन से सरणियों या शब्दकोशों में शून्य मान हो सकते हैं, और जो नहीं हो सकते हैं।
अगर आपको लगता है कि किसी सरणी में कभी [NSNull null]मान नहीं होते हैं, तो इसके लिए जाँच न करें। यदि कोई है [NSNull null], तो आपको एक अपवाद मिल सकता है लेकिन यह ठीक है: उद्देश्य-सी अपवाद प्रोग्रामिंग त्रुटियों को दर्शाते हैं। और आपके पास एक प्रोग्रामिंग त्रुटि है जिसे कुछ कोड बदलकर फिक्सिंग की आवश्यकता है।

यदि कोई वस्तु हो सकती है [NSNull null], तो आप इसके लिए बस परीक्षण करके देखें
(object == [NSNull null])isEqualऑब्जेक्ट के वर्ग को कॉल करना या जांचना बकवास है। केवल एक [NSNull null]वस्तु है, और इसके लिए सादे पुराने सी ऑपरेटर की जाँच सबसे सीधी और सबसे कुशल तरीके से ठीक है।

यदि आप एक ऐसी NSStringवस्तु की जाँच करते हैं जो हो नहीं सकती [NSNull null](क्योंकि आप जानते हैं कि यह नहीं हो सकती है [NSNull null]या क्योंकि आपने अभी जाँच की है कि यह अलग है [NSNull null], तो आपको अपने आप से यह पूछने की ज़रूरत है कि आप एक रिक्त स्ट्रिंग का इलाज कैसे करना चाहते हैं, यह लंबाई 0. है। यदि आप इसका उपचार एक nullस्ट्रिंग की तरह है nil, फिर परीक्षण करें (object.length == 0)। ऑब्जेक्ट.लिफ्ट 0 वापस आ जाएगा यदि object == nil, तो यह परीक्षण शून्य वस्तुओं और लंबाई के साथ तार को कवर करता है। 0. यदि आप एक स्ट्रिंग स्ट्रिंग से अलग 0 लंबाई का एक तार का इलाज करते हैं, तो बस जांचें कि क्या object == nil

अंत में, यदि आप एक स्ट्रिंग को एक सरणी या डिक्शनरी में जोड़ना चाहते हैं, और स्ट्रिंग शून्य हो सकती है, तो आपके पास इसे जोड़ने, इसे @""बदलने या इसके साथ प्रतिस्थापित करने का विकल्प नहीं है [NSNull null]। इसे बदलने का @""मतलब है कि आप "बिना स्ट्रिंग" और "लंबाई के स्ट्रिंग 0" के बीच अंतर करने की क्षमता खो देते हैं। इसे बदलने का [NSNull null]मतलब है कि आपको उस कोड को लिखना होगा जब आप उस सरणी या शब्दकोश तक पहुंचते हैं जो [NSNull null]वस्तुओं की जांच करता है।


बहुत लंबा है, लेकिन यह अच्छा है। NSNull को केवल सिंगल्स में APPEAR करना चाहिए! इस पूरे सवाल का कोई मतलब नहीं है, मुझे बताता है कि कोडर कुछ सही नहीं कर रहा था, और भविष्य में कई और भी, मैनुअल / अच्छे कोड अभ्यास नहीं पढ़े
स्टीफन जे

2

आप सिर्फ नील की जांच करें

if(data[@"Bonds"]==nil){
  NSLog(@"it is nil");
}

या

if ([data[@"Bonds"] isKindOfClass:[NSNull class]]) {
    NSLog(@"it is null");
}

2

मैक्रो सॉल्यूशन (2020)

यहाँ वह मैक्रो है जिसका उपयोग मैं एक स्ट्रिंग के लिए सुरक्षित स्ट्रिंग के लिए करता हूँ " (अशक्त) " स्ट्रिंग पर एक उदाहरण के लिए UILabel

#define SafeString(STRING) ([STRING length] == 0 ? @"" : STRING)

मान लें कि आपके पास एक सदस्य वर्ग और नाम संपत्ति है, और नाम शून्य है:

NSLog(@"%@", member.name); // prints (null) on UILabel

मैक्रो के साथ:

NSLog(@"%@", SafeString(member.name)); // prints empty string on UILabel

अच्छा और साफ 😊

एक्सटेंशन सॉल्यूशन (2020)

यदि आप अपने प्रोजेक्ट में नील नल और खाली स्ट्रिंग की जांच करना पसंद करते हैं, तो आप नीचे मेरी एक्सटेंशन लाइन का उपयोग कर सकते हैं:

NSString + Extension.h

///
/// Checks if giving String is an empty string or a nil object or a Null.
/// @param string string value to check.
///
+ (BOOL)isNullOrEmpty:(NSString*)string;

NSString + Extension.m

+ (BOOL)isNullOrEmpty:(NSString*)string {
    if (string) { // is not Nil
        NSRange range = [string rangeOfString:string];
        BOOL isEmpty = (range.length <= 0 || [string isEqualToString:@" "]);
        BOOL isNull = string == (id)[NSNull null];

        return (isNull || isEmpty);
    }

    return YES;
}

उदाहरण उपयोग

if (![NSString isNullOrEmpty:someTitle]) {
    // You can safely use on a Label or even add in an Array for example. Remember: Arrays don't like the nil values!
}



1
@interface NSString (StringFunctions)
- (BOOL) hasCharacters;
@end

@implementation NSString (StringFunctions)
- (BOOL) hasCharacters {
    if(self == (id)[NSNull null]) {
        return NO;
    }else {
        if([self length] == 0) {
            return NO;
        }
    }
    return YES;
}
@end

NSString *strOne = nil;
if([strOne hasCharacters]) {
    NSLog(@"%@",strOne);
}else {
    NSLog(@"String is Empty");
}

यह निम्नलिखित मामलों के साथ काम करेगा, NSString *strOne = @""या NSString *strOne = @"StackOverflow"OR NSString *strOne = [NSNull null]या NSString *strOne


0

यदि उस तरह की चीज पहले से मौजूद नहीं है, तो आप एक एनएसएसट्रिंग श्रेणी बना सकते हैं:

@interface NSString (TrucBiduleChoseAdditions)

- (BOOL)isEmpty;

@end

@implementation NSString (TrucBiduleChoseAdditions)

- (BOOL)isEmpty {
    return self == nil || [@"" isEqualToString:self];
}

@end

यह शायद overkill है और मुझे नहीं लगता कि यह इस समस्या को हल करेगा।
रोज

9
आत्म == शून्य व्यर्थ है - यदि स्वयं शून्य था, तो उद्देश्य C ने आपको पहले स्थान पर नहीं बुलाया होगा। [(NSString *) nil isEmpty] बस कभी भी आपके कोड को कॉल किए बिना 0 / nil / false लौटा देगा।
पीटर एन लुईस

4
दरअसल, इसके आगे, [(NSString *) nil isEmpty] झूठा वापस आ जाएगा। ऐसे Objective C तरीके लिखते समय, उन्हें परिभाषित करना बेहतर होता है, ताकि nil के 0 / nil / false का सही अर्थ हो, इसलिए विधि को हैचक्रैकर के रूप में लिखना बेहतर होगा। ध्यान दें कि लंबाई पहले से ही इसके लिए काम करती है, जैसा कि आप (s.length) कहीं भी उपयोग कर सकते हैं यदि आप (s.isEmpty) और s.length सही ढंग से s == नील मामले के लिए 0 वापस कर देंगे।
पीटर एन लुईस

यह एक गंभीर दुर्घटना है। आपने NSString के लिए "isEmpty" लागू किया है, लेकिन यदि यह वास्तव में NSNull है, तो isEmpty को NSNull में भेज दिया जाएगा, और क्रैश हो जाएगा क्योंकि यह उस संदेश का जवाब नहीं देता है!
daniel.gindi

0

मेरे लिए क्या काम करता है if ( !myobject )


3
यह अशक्त वस्तुओं के लिए काम नहीं करता है, केवल शून्य वस्तुओं के लिए। उदाहरण के लिए ... NSArray *testarray = [NSArray arrayWithObjects:[NSNull null],@"", nil]; NSString *string = [testarray objectAtIndex:0]; NSLog(@"null string value: %@",string); if (!string) { NSLog(@"string evaluates to null"); } if (string && (string==(id)[NSNull null])) { NSLog(@"string does not evaluate to null"); }
रिक स्मिथ-उन्नाव

Err .. प्रारूपण के बारे में खेद है, लेकिन कोड संकलन करेंगे :)
Rik Smith-Unna

0

अशक्त स्थितियों के लिए एक स्ट्रिंग की पूरी जाँच निम्नानुसार हो सकती है: <\ br>

    अगर (mystring)
     {
       अगर ([मिस्ट्रीइंग इक्वैलटॉस्ट्रिंग: @ ""])
        {
          रहस्यमय = @ "कुछ तार";
        }
     }    
    अन्य
     {
        // बयान
     }

0

मैं केवल नल स्ट्रिंग की जांच करता हूं

अगर ([myString isEqual: [NSNull null]])


0
if ([linkedStr isEqual:(id)[NSNull null]])
                {
                    _linkedinLbl.text=@"No";
                }else{
                    _linkedinLbl.text=@"Yes";
                }

1
हालांकि यह कोड स्निपेट प्रश्न का उत्तर दे सकता है, यह कैसे या क्यों की व्याख्या करने के लिए कोई संदर्भ प्रदान नहीं करता है। अपना उत्तर समझाने के लिए एक वाक्य या दो जोड़ने पर विचार करें।
ब्रैंडनस्क्रिप्ट

0
if ([strpass isEqual:[NSNull null]] || strpass==nil || [strpass isEqualToString:@"<null>"] || [strpass isEqualToString:@"(null)"] || strpass.length==0 || [strpass isEqualToString:@""])
{
    //string is blank  
}

0

स्ट्रिंग के लिए:

+ (BOOL) checkStringIsNotEmpty:(NSString*)string {
if (string == nil || string.length == 0) return NO;
return YES;

}

नीचे दी गई तस्वीर देखें:

यहां छवि विवरण दर्ज करें


0

स्ट्रिंग के लिए:

+ (BOOL) checkStringIsNotEmpty:(NSString*)string {
if (string == nil || string.length == 0) return NO;
return YES;}
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.