2016-09-01 9 views
0

Мне было интересно, существует ли «фиксированный порядок», в котором могут быть сделаны объявления C++? Я рассматриваю декларации в объявлении класса.C++ declare order (const/type/function)

В паскале я бы думать вдоль линий последовательности с использованием-Уст-типа функции:

  1. с использованием objpas; // целое число
  2. const c_limit = 5;
  3. тип t_int_array = массив [0..c_limit] целых чисел;
  4. function my_func (a_arg0: t_int_array): integer;

Мои объявления класса противоречат некоторым пользователям, потому что я использую приватно-охраняемый общественный порядок. Но в пределах этих разделов можно также зафиксировать порядок деклараций?

Вид вещей, которые я имею в виду, являются:

type declarations (types, enum, class etc) 
friend class 
friend functions 
static member value 
static functions 
virtual functions 
member function 
member value 
operators 
bitfields 
constructors 
destructors 
using clause 
(..plus any I may have missed?) 

Подоплека в том, что я работаю на графический интерфейс, который позволяет детям перетаскивать элементы (например, виртуальные функции) в списки (например, список виртуальных функций), поэтому для меня важны порядок этих списков.

В настоящий момент нет фиксированного порядка, согласно C++. Но если фиксированный порядок может быть доказан, чтобы работать, то это поможет «управлять» пользователями, чтобы увидеть, какие «списки» доступны, и отбрасывать элементы в них с просмотром min/max.

Одна из областей, в которых я не уверен, - это порядок, в котором объявлены функции и значения членов, потому что я не уверен, может ли член указывать на функцию класса. Я сильнее в pascal, чем C++, и буду благодарен за любые мысли по этому поводу?

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

+0

Вещи должны быть объявлены до их ссылки. Кроме этого, фиксированного порядка нет. – Barmar

+1

Элементы функции @Barmar inline могут ссылаться на участников, еще не объявленных. –

ответ

0

Нет универсального порядка, в котором вы можете разместить эти объявления участников. Вот контрпример для типов & констант:

struct One 
{ 
    static constexpr std::size_t dim = 4; 
    typedef float Array[dim]; 
}; 

struct Two 
{ 
    typedef float Data; 
    static constexpr std::size_t dataSize = sizeof(Data); 
}; 

А если принять во внимание decltype, то, конечно, любые две такие декларации виды могут зависеть друг от друга в обоих направлениях.

Кроме того, даже частный охраняемый общественный порядок не может быть зафиксирован. Рассмотрим этот класс:

struct Something 
{ 
public: 
    typedef std::pair<int, double> Data; 

    Data getData() const; 

private: 
    Data prepareData(); 
}; 

Однако для перетаскивания & падение UI, возможно, вы могли бы отделить декларацию представление пользовательского интерфейса и класса далее. Ничто не мешает вам представлять эти типы объявлений, сгруппированные в пользовательском интерфейсе, и рассеивать их в соответствии с их неявными зависимостями при создании определения класса из пользовательского интерфейса.

Да, это требует, чтобы вы анализировали объявления (или иным образом понимали их), чтобы выяснить их зависимости, но это выполнимо. Есть инструменты, такие как libclang, доступные для синтаксического анализа C++.

Он также предотвращает несколько дополнительных эффектов, которые могут быть достигнуты с порядком декларации и наследованием (1), но это не должно быть проблемой в среде, ориентированной на новичков.


(1) Пример такой трюк:

struct Base 
{ 
    typedef int Buddy; 
}; 

struct Derived : Base 
{ 
    Buddy getInt(); 
    typedef Buddy float; 
    Buddy getFloat(); 
}; 
+0

В отношении частного-частного примера struct Something, может ли typedef Data быть помещен вне класса? Таким образом, порядок раздела может быть частно-публичным? Думаю, я все еще думаю о паскале, где (я думаю) типы не объявляются внутри классов. Или это будет слишком ограничительным в других примерах, не приведенных здесь? –

+0

В отношении рассеяния элементов объявление класса и определение класса помещаются в разные файлы (* .C++, *. H), графический интерфейс может сочетаться как визуально. Мое предпочтение заключается в том, что заголовочные файлы содержат спецификации и файлы блоков, чтобы содержать элементы реализации. Бармар упоминается в предыдущем комментарии о встроенных функциях-членах, ссылающихся на членов, которые еще не объявлены, так что это может решить и эту проблему? –

+0

@MichaelCollier Re: вне класса 'Data'. Технически это можно было объявить вне класса. Но затем он загрязняет пространство имен, и вы не можете иметь такие вещи, как 'std :: vector :: iterator' и т. Д. Вы можете, конечно, ввести фиксированный порядок, когда вы накладываете достаточные ограничения на то, какие биты C++ разрешены; но если вы это сделаете, зачем вообще заниматься C++? – Angew

0

Может ли это быть возможным решением?

Я принял во внимание необходимость объявления констант и типов в любом порядке и что они должны быть выполнены до чего-либо еще.

Кроме того, тело кода не может быть помещено внутри объявления функции в классе.

После этого могут ли быть отредактированы разделы, указанные ниже, в том порядке, который я дал, или действительно в любом другом/более выгодном порядке?

class t_maybe_this_will_work 
{ 
    //1. 
    // This MUST be first, and allow declarations in ANY order 
    // constexpr,typedefs,enums,nested classes 

    //2. 
    // What is best/only order for these..? 
    // I have listed them so that functions come before values in case 
    // functions are referenced? 

    // friend     classes 
    // friend     functions 
    // using     clauses 

    // static     functions 
    // virtual     functions 
    // virtual     operator 
    // non-static,non-virtual function 
    // non-static,non-virtual operator 

    // static     value 
    // non-static    value 
    // bitfield    value 

    // virtual     destructors 
    // non-virtual    destructors 
    //       constructors 

    /*  ***** RULE ***** 

    The body of functions are NOT defined within the class. 

    int not_allowed_body_here (void) 
    { 
     // defining some code here... 
    } ; 

    */ 

} ;