C++重新引导变量在一段时间内循环

发布于 2025-02-11 15:46:52 字数 3642 浏览 2 评论 0原文

我有一个设置菜单,可以使窗口完整屏幕。大多数菜单元素取决于窗口大小。默认情况下,所有菜单元素都处于调整窗口大小之前的位置(这意味着它们不在我打算的位置)。我了解该位置需要重新计算,但是在这种情况下,我刚刚称呼菜单中所有元素的位置的函数,而是刚刚称为初始load()函数。

这是一个可以帮助的代码摘要:

     while(!exit) {
      switch(State) {
        case Menu:
        
          Menu settings = Menu(...);
          settings.load() //load here

          while(State == Menu) {
            
            if (window.fullscreen()) {
              settings.load(); //reload here
            }
            
          }//end while
        break;
        default:
        break;
      }//end switch
    }//end while

这有效,但是我担心load()首次调用时使用的内存。变量使用相同的名称,但是创建了新对象吗?他们被覆盖了吗?我第一次加载菜单时存储对象的内存发生了什么?

此外,这里正在加载和重新加载的“什么”是std :: simelod_ptr< table>,使std :: vector< std :: peak< std :: sumelit_ptr< textrect>>

编辑:设置类:

class Settings {

  Window& _window;
  sf::RenderWindow& _win;
  //MainState& _mainState;
  MenuState& _menuState;
  Resources& _res;
  Input& _input;

  std::unique_ptr<TextRect> SettingsBanner;
  std::unique_ptr<Table> SettingsMenu;
  std::unique_ptr<Table> SettingsSave;

public:

  Settings(Window& pWindow
          ,MainState& pMainState
          ,MenuState& pMenuState
          ,Resources& pResources
          ,Input& pInput
          );
  ~Settings();

  void load();
  void update();

private:

  void inputs();

};

load()

void Settings::load() {

  //all kinds of variables

  SettingsBanner = std::make_unique<TextRect>(_win
                                             ,string
                                             ,font
                                             ,texture
                                             ,sf::Color::White
                                             ,size
                                             ,origin
                                             ,position
                                             ,sf::Color::White
                                             ,outColor
                                             ,charSize
                                             ,outline
                                             );

  //more variables

  SettingsMenu = std::make_unique<Table>(_win
                                        ,font
                                        ,texture
                                        ,textureColor
                                        ,fillColor
                                        ,outColor
                                        ,charSize
                                        ,outline
                                      );

  SettingsMenu->element("FullScreen");
  SettingsMenu->element("VSync");
  SettingsMenu->element("FrameRate");
  SettingsMenu->element("Volume");

  SettingsMenu->makeTable("CenterLeft", position, rowCol);

  //more variables

  SettingsSave = std::make_unique<Table>(_win
                                        ,font
                                        ,texture
                                        ,textureColor
                                        ,fillColor
                                        ,outColor
                                        ,charSize
                                        ,outline
                                        );

  SettingsSave->element("Save");
  SettingsSave->element("Back");

  SettingsSave->makeTable("BottomRight", position, rowCol);

}// end func

I have a settings menu that can make the window fullscreen. Most of the menu elements are dependent on the window size. By default, all the menu elements are in the same position they were in before the window was resized (meaning they are not in the position I intend). I understand the positions needs to be recalculated, but in this instance, rather than create a function that resets the position of all the elements in the menu, I've just called the initial load() function.

Here is a code summary to help:

     while(!exit) {
      switch(State) {
        case Menu:
        
          Menu settings = Menu(...);
          settings.load() //load here

          while(State == Menu) {
            
            if (window.fullscreen()) {
              settings.load(); //reload here
            }
            
          }//end while
        break;
        default:
        break;
      }//end switch
    }//end while

This works, but I'm worried about the memory used by load() when it was first called. The variables use the same name, but are new objects created? Are they overwritten? What happened to the memory that stored the objects when I first loaded the menu?

Also, the "What" that is being loaded and reloaded here is a std::unique_ptr<Table> that makes a std::vector<std::pair<std::string, std::unique_ptr<TextRect>>>.

Edit: the Settings class:

class Settings {

  Window& _window;
  sf::RenderWindow& _win;
  //MainState& _mainState;
  MenuState& _menuState;
  Resources& _res;
  Input& _input;

  std::unique_ptr<TextRect> SettingsBanner;
  std::unique_ptr<Table> SettingsMenu;
  std::unique_ptr<Table> SettingsSave;

public:

  Settings(Window& pWindow
          ,MainState& pMainState
          ,MenuState& pMenuState
          ,Resources& pResources
          ,Input& pInput
          );
  ~Settings();

  void load();
  void update();

private:

  void inputs();

};

and the load():

void Settings::load() {

  //all kinds of variables

  SettingsBanner = std::make_unique<TextRect>(_win
                                             ,string
                                             ,font
                                             ,texture
                                             ,sf::Color::White
                                             ,size
                                             ,origin
                                             ,position
                                             ,sf::Color::White
                                             ,outColor
                                             ,charSize
                                             ,outline
                                             );

  //more variables

  SettingsMenu = std::make_unique<Table>(_win
                                        ,font
                                        ,texture
                                        ,textureColor
                                        ,fillColor
                                        ,outColor
                                        ,charSize
                                        ,outline
                                      );

  SettingsMenu->element("FullScreen");
  SettingsMenu->element("VSync");
  SettingsMenu->element("FrameRate");
  SettingsMenu->element("Volume");

  SettingsMenu->makeTable("CenterLeft", position, rowCol);

  //more variables

  SettingsSave = std::make_unique<Table>(_win
                                        ,font
                                        ,texture
                                        ,textureColor
                                        ,fillColor
                                        ,outColor
                                        ,charSize
                                        ,outline
                                        );

  SettingsSave->element("Save");
  SettingsSave->element("Back");

  SettingsSave->makeTable("BottomRight", position, rowCol);

}// end func

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

榆西 2025-02-18 15:46:52

简而言之:std :: make_unique每次调用时都会制作新对象。它不能重复使用上一个对象的内存。如果新对象的构造函数会抛出异常,会发生什么?仅在分配到现有unique_ptr的分配中,就会丢弃旧对象,如果抛出异常,您将不会到达那里。这样可以确保例外安全

您当然可以以不同的方式编写设置:: load()。如果settingsbanner不是空的,则可以分配给*settingsbanner而不是调用std :: make_unique

In short: std::make_unique makes new objects, every time it's called. It cannot reuse the memory of the previous object. What would happen if the constructor of the new object throws an exception? It's only in the assignment to the existing unique_ptr that the old object is discarded, and you wouldn't get there if an exception is thrown. This ensures exception safety.

You can of course write Settings::load() in different ways. If SettingsBanner is not empty, you can assign to *SettingsBanner instead of calling std::make_unique.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文