本文介绍了在Objective C ++代码中,合成属性设置程序未调用Copy构造函数的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们都知道Objective-C ++的文档稀疏.我什么都找不到,但是我也很难找到合适的明确搜索词.因此,希望通过Stackoverflow进行救援!

We all know how sparsely documented Objective-C++ is. I can't find anything on this, but I'm also finding it hard to find suitable unambiguous search terms.So, Stackoverflow to the rescue (I hope)!

我有一个C ++类,我在Objective-C(++)类中有一个实例(并且我启用了用于调用构造函数/析构函数的项目设置).

I have a C++ class that I have an instance of within an Objective-C(++) class (and I have the project setting enabled for constructors/ destructors to be called).

一切正常,直到我尝试通过@synthesize d属性公开实例.我将其设为assign属性(因为Obj-C保留计数不适用).该属性似乎可以正常工作,但是当我设置实例时,我希望复制构造函数会参与其中.我实际上看到的是创建了一个临时实例(调用了那个的副本构造函数)-这是所期望的.但是在ivar实例上的副本构造函数是 not 调用的.这些值是神奇地"设置的.我假定@synthesize d代码正在做类似memcpy的操作作为最后一步.这对于C struct很好,但对于C ++ class es却没有太大帮助,在C ++ class中,代码的正确性取决于适当地调用复制构造函数和赋值运算符.

This all works fine until I try to expose the instance via a @synthesized property. I make it an assign property (as Obj-C retain counting is not applicable). The property appears to work except when I set the instance I would expect the copy constructor to be involved.What I actually see is that a temporary instance is created (the copy constructor on that is invoked) - which is all expected. But the copy constructor on the ivar instance is not called. The values are "magically" set. I'm presuming that the @synthesized code is doing something like a memcpy as the final step. This is fine for C structs, but not so helpful for C++ classes where the correctness of the code depends on the copy constructors and assignment operators being called appropriately.

是否有人更深入地研究,使它起作用,或确认不可能将C ++对象作为ivars保留在Obj-C(++)类中,并且没有由@synthesize d调用的复制构造函数财产设定者?

Has anyone looked into this in any more depth, got it working, or confirmed that it is not possible to hold C++ objects as ivars in an Obj-C(++) class and have copy constructors called by @synthesized property setters?

(如果需要,我可以为所有这些发布示例代码-但即使是最低版本也是如此).

(I can post sample code for all this if necessary - but even the minimal version is a screenful or so).

推荐答案

嗯,如果我不感到困惑,则不调用复制构造函数是完全合理的.您是否希望ivar被魔术般地破坏和复制构建?我想这违反了C ++的规则.如果合成的二传手在概念上是

Uhm, if I'm not confused, it's perfectly reasonable that the copy constructor is not called. Do you expect that ivar to be magically destructed and copy-constructed? I guess that's against C++'s rules. If the synthesized setter is conceptually

-(void)setFoo:(Foo)foo_{
    foo=foo_;
}

然后应调用operator=,而不是复制构造函数.

then operator= should be called, rather than the copy constructor.

话虽如此operator=也不会被称为笨蛋"(10.6.4,gcc 4.2.1)!这是示例代码:

That said, the operator= is not called either, bummer (10.6.4, gcc 4.2.1.)! Here's the sample code:

#import <Foundation/Foundation.h>

class Foo{
    int a,b;
public:
    Foo():a(0),b(0){NSLog(@"default constructor for %p",this);}
    Foo(const Foo&foo):a(foo.a),b(foo.b){NSLog(@"copy constructor for %p",this);}
    Foo& operator=(const Foo& foo){
    NSLog(@"assignment operator for %p",this);
        a=foo.a;
        b=foo.b;
        return *this;
    }
};

@interface Bar:NSObject {
    Foo foo;
}
@property (assign) Foo foo;
@end

@implementation Bar
@synthesize foo;
@end

int main(){
    NSAutoreleasePool *pool=[[NSAutoreleasePool alloc] init];
    Bar* bar=[[Bar alloc] init];
    Foo foo;
    bar.foo=foo;
    [pool drain];
}

将其保存到boo.mm中,

$ g++ -fobjc-call-cxx-cdtors boo.mm -framework Foundation
$ ./a.out
2010-09-04 12:32:06.570 a.out[24352:903] default constructor for 0x10010cdc8
2010-09-04 12:32:06.572 a.out[24352:903] default constructor for 0x7fff5fbff7e0
2010-09-04 12:32:06.573 a.out[24352:903] copy constructor for 0x7fff5fbff7d0
$

现在,我有了上面写的显式二传手,而不是@synthesize Foo,我正确地拥有了

Now, I had the explicit setter I wrote above instead of @synthesize Foo, I correctly had

$ ./a.out
2010-09-04 12:42:22.206 a.out[24417:903] default constructor for 0x10010cdc8
2010-09-04 12:42:22.209 a.out[24417:903] default constructor for 0x7fff5fbff7e0
2010-09-04 12:42:22.210 a.out[24417:903] copy constructor for 0x7fff5fbff7d0
2010-09-04 12:42:22.210 a.out[24417:903] assignment operator for 0x10010cdc8

用于生成综合设置器的clang源代码为,请参见GenerateObjCSetter.在那里,它最终测试是否需要C ++赋值运算符.我会说这是一个灰色地带,没有详细记录,但目前正在实施中...

The clang source code for the generation of the synthesized setter is this, see GenerateObjCSetter. There, it eventually tests whether C++ assignment operator is needed. I would say it's a gray area, not well-documented but currently being implemented...

这篇关于在Objective C ++代码中,合成属性设置程序未调用Copy构造函数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-13 22:11