如何在C ++ 11中使用decltype引用当前类?

时间:2013-11-25 21:24:44

标签: c++ c++11 static-methods decltype

当我声明一个类静态方法时,是否可以使用decltype(或任何其他类似的样式)引用当前类?例如,

class
AAA
{
    static AAA const make();
};

我正在尝试制作这样的东西。

class
AAA
{
    static decltype(*this) const make();  // Not working because there's no `this`.
};

*this用于描述我想要做的事情。我想知道一些可以解析为decltype()的{​​{1}}表达式。

如果有可能我该怎么做?

3 个答案:

答案 0 :(得分:5)

在C ++中你可以这样做:

class
AAA
{
public:
    static auto make()
    {
        return AAA();
    }
};

int main()
{
    AAA aaa = AAA::make();
}

这在C ++ 11中是不合法的,因为您需要为make()指定返回类型。在C ++ 98/03/11中,您可以:

class
AAA
{
public:
    typedef AAA Self;

    static Self make()
    {
        return AAA();
    }
};

这是低技术,但非常易读。

<aside>

您应该避免按值返回const限定类型。这抑制了有效的移动语义。如果要避免分配给rvalues,请创建一个使用&限定的赋值运算符。

</aside>

答案 1 :(得分:0)

你也许可以这样做:

#include<iostream>

class AAA
{
   int _i;

   public:
   AAA(int i): _i(i) {}

   static auto make(int i) -> typename std::remove_reference<decltype(*this)>::type
   {
      return {i};
   }

   void print()
   {
      std::cout << _i << std::endl;
   }
};

int main()
{
    AAA aaa = AAA::make(1);
    aaa.print();
    return 0;
}

它至少在GCC 4.7.2上编译:)

<小时/> 编辑26 / 11-13:上面的代码不是合法的c ++,即使它用gcc编译,它也不与clang或icpc编译。我道歉。

答案 2 :(得分:0)

刚刚发明了一种使用成员指针的方式,它似乎有效: https://godbolt.org/z/v-g5z0

using (Html.BeginForm("SaveUser", "BlogUser", FormMethod.Post, new { @class = "form-horizontal", enctype = "multipart/form-data" }))
{
    <div class="form-group">
        @Html.HiddenFor(x => x.Id)
        @Html.HiddenFor(x => x.ProfileImage)
        @Html.HiddenFor(x => x.UserName)
        @Html.HiddenFor(x => x.Password)
        @Html.HiddenFor(x => x.Role)
        <div class="col-sm-10">
            <label>Jméno</label>
        </div>
        <div class="col-sm-10">
            @Html.TextBoxFor(x => x.Name, new { @class = "form-control" })
            @Html.ValidationMessageFor(x => x.Name)
        </div>
    </div>
    <div class="form-group">
        <div class="col-sm-10">
            <label>Příjmení</label>
        </div>
        <div class="col-sm-10">
            @Html.TextBoxFor(x => x.Surname, new { @class = "form-control" })
            @Html.ValidationMessageFor(x => x.Surname)
        </div>
    </div>
    <div class="form-group">
        <div class="col-sm-10">
            <label>Profilový obrázek</label>
        </div>
        <div class="col-sm-10">
            <input type="file" name="picture" />
            @if (!String.IsNullOrEmpty(Model.ProfileImage))
                {
                <img src="@Url.Content("~/Upload/UserImages/" + Model.ProfileImage)" />
            }
        </div>
    </div>
        <div class="form-group">
            <div class="col-sm-10">
                <label>Něco o mně</label>
            </div>
            <div class="col-sm-10">
                @Html.TextAreaFor(x => x.About, new { @class = "form-control formatedText", @rows = 20 })
                @Html.ValidationMessageFor(x => x.About)
            </div>
        </div>
            <div class="form-group">
                <div class="col-sm-10">
                    <button type="submit" class="btn btn-primary btn-lg btn-block">Uložit</button>
                </div>
            </div>
}

这也不完美,它需要-fpermissive与gcc一起编译, 但至少gcc / VS /英特尔都编译它,它的工作原理。 事实上,gcc / mingw甚至不需要-fpermissive。