Вопрос

Я использую C ++ .NET 2.0

У меня есть 2 формы

первый из них объявлен следующим образом

#include "stdafx.h"
    namespace myNamespace{

      public ref class frmMain : public System::Windows::Forms::Form {
      /*... snip ...*/
      public void addNewRow(String^ text){ /*... snip... */  }
      public void launchSubForm() { SubForm^ sf = gcnew SubForm(this); sf->Show(); }

      };
    }

второй вариант выглядит следующим образом

#include stdafx.h
    namespace myNamespace{
      ref class frmMain;
      public ref class SubForm : public System::Windows::Forms::Form {
      frmMain^ myMain;
      SubForm ( frmMain^ pMain){
        myMain = pMain;
      }
      /*... snip ...*/
      public void exportRows(String^ text){ /*... snip... */  }
        myMain->addNewRow("myNewText");   <--- This line causes compile error
      };
    }

в stdafx.h у меня есть

/*... snip... */
#include "SubForm.h"
#include "frmMain.h"

Теперь к вопросу!Строка в подчиненной форме заставляет компилятор сообщать мне "использование неопределенного типа MyNamespace::frmMain

Я действительно понятия не имею, почему "ref class frmMain" не решает эту проблему

Это было полезно?

Решение

Это происходит потому, что и то, и другое из этих заголовочных файлов включает "stdafx.h", а stdafx.h включает "SubForm.h" до того , как "frmMain.h".

Итак, в "Подчиненной форме.h" компилятор хочет определить подчиненную форму до того, как был определен frmMain, что приводит к ошибке.

Правильный способ решить эту проблему - сохранить весь код для ваших классов в соответствующем исходном файле и не в заголовке.Если ваш заголовочный файл просто объявляет:

public void exportRows(String^ text);

тогда вы можете определить:

public void SubForm::exportRows(String^ text)
{
    /*... snip ...*/
    myMain->addNewRow("myNewText");
}

в SubForm.cpp, и все должно получиться великолепно.


Редактировать: Хороший объектно-ориентированный дизайн предполагает отделение интерфейса от реализации, и лучший способ добиться этого на C ++ - сохранить интерфейсы в файлах заголовков, а код реализации - в соответствующих исходных файлах.

Суть в том, что ваши заголовочные файлы должны содержать только заявления.Думайте о них как об интерфейсе к вашим классам.Заголовочный файл показывает только сигнатуры функций, которые будет реализовывать ваш класс.Исходные файлы, с другой стороны, содержат все определения, которые являются реализацией ваших классов.

Другие советы

В C ++ вы можете пересылать объявление класса только в том случае, если вы не вызываете метод по указателю или ссылке на этот класс.Каждый раз, когда вы пытаетесь вызвать метод для указателя на класс или ссылки, вам необходимо иметь доступное определение класса.

Удаление неполного типа законно, но очень опасно.

Пожалуйста, используйте тег, отличный от C ++, так как это не C ++.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top