У меня есть много кода на С#, который я должен написать на С++. У меня мало опыта в С++.
Я использую Visual Studio 2012 для сборки. Проект является Статической библиотекой в С++ (не в С++/CLI).
У меня есть класс со статическим методом со статическим частным членом. Когда я отлаживаю, я вижу, как вызывается как создатель Constructor, так и Copy Constructor. Я не понимаю, почему оба вызываются, я думал, что только один будет. Есть ли способ, которым я могу заставить вызвать только один конструктор?
Это мой код
MyClass& MyClass::MyInstance()
{
static MyClass myLocalVariable = MyClass(/*parameters*/);
return myLocalVariable ;
}
При вызове метода MyInstance:
Возможно ли, что экземпляр, хранящийся myLocalVariable, является только временным и может быть уничтожен позже?
Update:
Так как некоторые люди не могут воспроизвести мою проблему, я добавляю здесь больше кода. У меня есть 3 проекта с одинаковым поведением (один из них - статическая библиотека, которую я вызываю из своих тестов Unit, а остальные 2 - Win32 Console Applications)
С++ Main
int _tmain(int argc, _TCHAR* argv[])
{
MyClass& instance = MyClass::MyInstance();
return 0;
}
С++ MyClass.h
#pragma once
#include <string>
using namespace std;
class MyClass
{
private:
string name;
public:
MyClass(void);
MyClass(string name);
MyClass(const MyClass&);
~MyClass(void);
static MyClass& MyInstance();
};
С++ MyClass.cpp
#include "MyClass.h"
#include <iostream>
using std::cout;
MyClass::MyClass(void)
{
cout << "Empty Cons\n";
}
MyClass::MyClass(string name)
{
this->name = name;
cout << "Parameters Cons\n";
}
MyClass::MyClass(const MyClass& myClass)
{
name = myClass.name;
cout << "Copy Cons\n";
}
MyClass::~MyClass(void)
{
cout << "Destructor\n";
}
MyClass& MyClass::MyInstance()
{
cout << "MyInstance\n";
static MyClass myInstance = MyClass("MyClassName");
return myInstance;
}
Мой вывод:
MyInstance
Параметры минус
Копирование минусов
деструктор
Просто напишите переменную как
static MyClass instance;
если нет параметров, или
static MyClass instance(foo, bar);
если есть. Или, поскольку это MSVC 2012, может поддерживаться единообразный синтаксис инициализации:
static MyClass instance{/*args here, could be empty*/};
Это приведет к инициализации переменной на месте вместо инициализации временного и копирования ее в цель. (Компилятору будет разрешено опустить копию, но, по-видимому, это не так.)
Возможно ли, что экземпляр, хранящийся myLocalVariable, является только временным
Обратите внимание, что во-первых, правильное слово является "временным", а второе, myLocalVariable
является экземпляром, оно не удерживает его. Если вы явно не используете указатели или ссылки, объекты С++ ведут себя скорее как структуры С#, чем классы, поскольку переменные не содержат ссылок, они действительно являются объектами.
Возможно ли, что экземпляр, хранящийся myLocalVariable, является только временным и может быть уничтожен позже?
myLocalVariable статичен, поэтому не будет уничтожен и будет доступен каждый раз, когда вы вызываете MyInstance
MyClass& MyClass::MyInstance()
{
static MyClass myLocalVariable = MyClass(/*parameters*/);
return myLocalVariable ;
}
Это вызовет только 1 конструктор, который является конструктором param, поскольку myLocalVariable возвращается по ссылке, а не по значению.
static MyClass myLocalVariable(/*parameters*/);
, Это должно быть эквивалентно тому, что у вас есть, по крайней мере для обычных переменных на основе стека.