Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/145.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
std::函数成员可以访问其他成员吗? 我正在制作一个小型的塔防游戏,以练习C++。我知道其他语言,但在C++中几乎没有什么实际开发。 在这个游戏中,我将有几个建筑,所以我制作了一个类似这样的类: class Building { private: sf::Sprite& sprite; float timer = 0; void update(float delta); };_C++_C++11_Lambda - Fatal编程技术网

std::函数成员可以访问其他成员吗? 我正在制作一个小型的塔防游戏,以练习C++。我知道其他语言,但在C++中几乎没有什么实际开发。 在这个游戏中,我将有几个建筑,所以我制作了一个类似这样的类: class Building { private: sf::Sprite& sprite; float timer = 0; void update(float delta); };

std::函数成员可以访问其他成员吗? 我正在制作一个小型的塔防游戏,以练习C++。我知道其他语言,但在C++中几乎没有什么实际开发。 在这个游戏中,我将有几个建筑,所以我制作了一个类似这样的类: class Building { private: sf::Sprite& sprite; float timer = 0; void update(float delta); };,c++,c++11,lambda,C++,C++11,Lambda,现在,我会有很多不同的建筑,但它们都应该有相同的成员。现在,在Java中,我将(必须)为每种不同类型的建筑创建一个子类,但我在想,我可以更改void update(float delta)到std::函数更新并具有创建不同建筑的工厂功能?我想象的是这样的: 在h楼: class Building { private: sf::Sprite& sprite; float timer = 0; std::function<void(float)> upda

现在,我会有很多不同的建筑,但它们都应该有相同的成员。现在,在Java中,我将(必须)为每种不同类型的建筑创建一个子类,但我在想,我可以更改
void update(float delta)
std::函数更新并具有创建不同建筑的工厂功能?我想象的是这样的:

在h楼:

class Building
{
private:
    sf::Sprite& sprite;
    float timer = 0;
    std::function<void(float)> update;
};
班级建设
{
私人:
雪碧&雪碧;
浮动计时器=0;
功能更新;
};
和在building.cpp中

Building getBuildingA()
{
    Building b;
    b.sprite = /* ... */
    b.update = [](float delta) {
        std::cout << timer++ << std::endl;
    };
    return b;
}
Building-getBuildingA()
{
b楼;
b、 雪碧=/**/
b、 更新=[](浮点增量){

std::cout您可以将lambda捕获
设置为this

class Building
{
private:
    sf::Sprite& sprite;
    float timer = 0;
    std::function<void(Building*, float)> update_impl;
    void update(float x) { update_impl(this, x); }
};
班级建设
{
私人:
雪碧&雪碧;
浮动计时器=0;
std::函数更新\u impl;
无效更新(float x){update_impl(this,x);}
};
但实际上,基于您设计的这一部分,看起来您真的应该使用子类和虚拟函数;这就是它们的用途

function
的典型应用是在传递函数对象时——例如,用一个方法代替编写接口类的Java范例,尤其是在只编写函数或lambda而不是整个对象的设置中


对于对象多态性,子类化和虚拟函数的主要替代方法是使用模板和泛型编程——尽管这主要适用于需要在编译时发生多态性的情况(我认为这不适合您的情况)

您可以简单地捕获
这一点
例如:

struct S {
    auto foo() {
        return [this](){ this->bar(); };
    }

    void bar() { }
};

int main() {
    S s;
    s.foo()();
}
#include<cassert>

struct S {
    auto foo() {
        return [timer = timer](){
            assert(timer == 42);
        };
    }

    int timer{42};
};

int main() {
    S s{};
    s.foo()();
}
如果您使用的是C++14,则可以改用初始值设定项列表。
例如:

struct S {
    auto foo() {
        return [this](){ this->bar(); };
    }

    void bar() { }
};

int main() {
    S s;
    s.foo()();
}
#include<cassert>

struct S {
    auto foo() {
        return [timer = timer](){
            assert(timer == 42);
        };
    }

    int timer{42};
};

int main() {
    S s{};
    s.foo()();
}
#包括
结构{
自动foo(){
返回[timer=timer](){
断言(计时器==42);
};
}
整数计时器{42};
};
int main(){
S{};
s、 foo()();
}

这样,您将获得一个名为timer的副本初始化变量,该变量将在lambda函数体中使用。

您可以通过使用Building的静态成员函数来提供factory类来解决隐私问题

您将遇到的第二个问题是,您正在按值返回建筑,因此,除非发生RVO,否则您将不知道要返回的对象的最终地址。您可以通过让“update()”函数将其作为参数传递来解决此问题

#include <iostream>
#include <functional>

class Building {
    // C++ classes are private by default
    int timer_;
    std::function<void(Building*)> update_;

public:
    void update() {
        update_(this);
    }

    static Building getBuildingA() {
        Building b;
        b.timer_ = 42;
        b.update_ = [](Building* b) {
            b->timer_++;
            std::cout << b->timer_ << '\n';
        };
    }
};

int main() {
    Building b = Building::getBuildingA();
    b.update();
    return 0;
}
#包括
#包括
班级建设{
/C++类默认为私有类
int定时器;
std::函数更新;
公众:
无效更新(){
更新(本);
}
静态建筑getBuildingA(){
b楼;
b、 计时器u42;
b、 更新=[](建筑物*b){
b->timer_uz++;

std::cout timer_uuu通过捕获
?您不能通过这样的赋值来初始化引用。它必须在初始值设定项列表中初始化。您可以通过使getBuildingA成为Building的静态成员函数来解决隐私问题。回答得好,谢谢。我明白您关于子类化的观点。这里还有其他问题我的设计,但它是为了探索lambdas和类似的东西可以做什么。为了完整性,我还可以想象
函数
也适用的设计;我这里没有完整的图片,所以我的部分建议取决于有根据的猜测。啊,我想我特别想尝试
函数
是我遗漏的完整图片的相关部分。:)