【问题标题】:NSString pointer passed to function... not keeping the value I setNSString 指针传递给函数...不保持我设置的值
【发布时间】:2012-07-02 23:21:05
【问题描述】:

我不确定我在这里做错了什么。我还尝试使用以下方法在foo 中设置s1..3

s1 = [[NSString alloc] initWithString:[filepaths objectAtIndex:0]];

上下文如下:

void foo(NSString *s1, NSString *s2, NSString *s3){
    //assign long string to NSString *fps
    //...
    //break fps into smaller bits
    NSArray *filepaths = [fps componentsSeparatedByString:@"\n"];
    //the above worked! now let's assign them to the pointers
    s1 = [filepaths objectAtIndex:0];
    //repeat for s2 and s3
    NSLog(@"%@",s1); //it worked! we're done in this function
}

int main(int argc, const char * argv[]){
    NSString *s1 = nil; //s2 and s3 as well
    foo(s1,s2,s3); //this should work
    NSLog(@"%@",s1); //UH OH, this is null!
    return 0;
}

【问题讨论】:

    标签: cocoa pointers parameter-passing


    【解决方案1】:

    没有。

    您正在传递指向可以在本地变异的对象的指针。您没有更改原始对象,正如您可能从普通 C 中想到的那样。

    如果你想使用这种方法(我推荐 - 除了NSError 的情况外,在 Cocoa 中看到它真的很奇怪),你会得到类似的东西:

    void foo(NSString **s1, NSString **s2, NSString **s3) {
        *s1 = [filepaths objectAtIndex:0]; // etc.
    }
    

    然后您将传入&s1 作为参数。

    这当然会破坏s1 中的任何内容,可能会导致内存泄漏、线程不安全等,除非您非常小心。这就是为什么我说你通常不会这样做。

    【讨论】:

    • 它是一个简短的、相对简单的命令行程序,但 Foundation 和 Scripting Bridge 框架派上用场,所以它在 Obj-C 中。另外,将此归咎于自上次我需要或考虑传递指针以来已经过去了几年。
    • @ray 在 Objective-C 中编写命令行程序没有错;事实上,我今天早上就在邮件列表上向某人推荐了这个。我只是建议您换个思路:让该方法返回一个包含您的字符串的 NSArray。更简单,更清晰,不太可能在其他地方引起问题。
    • @ray 我不是 100% 确定,但我认为 C 中按引用返回的约定在很大程度上是由于 C 中几乎完全缺乏集合原语(甚至是数组只是一个美化的指针),在 Objective-C 中不是问题。
    【解决方案2】:

    函数获取其参数的本地副本,因此您正在修改 NSString* 的副本而不是原始副本。这称为“按值传递”。你想要的是“通过引用传递”,它看起来像这样:

    void foo(NSString** s1) {
        if(s1) *s1 = @"Different string";
    }
    
    int main(int argc, const char* argv[]){
        NSString* s1 = nil;
        foo(&s1);
        NSLog(@"%@", s1);
        return EXIT_SUCCESS;
    }
    

    这归结为您对 C 中的指针的理解程度。最好阅读运算符 & 的“地址”和取消引用运算符 *,以及一般情况下的 C 指针。

    【讨论】:

      猜你喜欢
      • 2019-02-13
      • 1970-01-01
      • 2012-03-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-08-20
      • 1970-01-01
      相关资源
      最近更新 更多