Re: Инициализация локальной статической переменной
От: zaufi Земля  
Дата: 22.11.10 18:10
Оценка: 1 (1) +2
мое imho в таких случаях: если foo() находится в .cpp то помещаем get_black() в анонимное пространство имен гденить выше, если же она в hpp, то помещаем в пространство имен details (заключенное в текущее пространство имен...). само имя details явно указывает что никто, исключая текущую библиотеку\подсистему\whatever не должен снаружи использовать сущьности из него...
Re[3]: Инициализация локальной статической переменной
От: zaufi Земля  
Дата: 23.11.10 06:39
Оценка: 6 (1)
Здравствуйте, pasenger, Вы писали:

P>Здравствуйте, zaufi, Вы писали:


Z>>мое imho в таких случаях: если foo() находится в .cpp то помещаем get_black() в анонимное пространство имен гденить выше, если же она в hpp, то помещаем в пространство имен details (заключенное в текущее пространство имен...). само имя details явно указывает что никто, исключая текущую библиотеку\подсистему\whatever не должен снаружи использовать сущьности из него...


P>Я тоже помещаю в таких случаях случаях функции в анонимный namespace. Но в результате получается куча функций, которые которые вызываются только в одном месте. А данная конкретная функция так и вовсе вызывается один раз. Это деструктурирует файл и ухудшает читаемость (на мой вкус)


выноси все это в отдельные файлики типа там blah/details/get_black.hh (и пространство имен blah::details) если уж так не хочется "загрязнять" файлы с реализацией... -- сам для себя решай что тебе больше подходит: плодить файлики или немножко сделать "нечитаемым" код...

но в принципе ничо в этом страшного нет (и в том чтобы оставить и в том чтобы вынести ) -- посмотри вон на буст ну да... смотреть в его исходники без "взрыва мозга" могут не все подряд, но с другой стороны у них документация одна из лучших в опен соурсе (и практически избавляет от необходимости лазить по сорцам)... попробуй и ты стремиться в эту сторону ... смысле делать доки для своего кода такими, чтоб тому кто пользуется не нужно было лазить в исходники
правда встает другая дилемма: хорошая doxygen документация также "загрязняет" код -- ну по крайней мере если не выыносить ее в отдельные файлы... что вобщем то я за свою практику встречал пару раз %)
Re[5]: Инициализация локальной статической переменной
От: zaufi Земля  
Дата: 24.11.10 00:44
Оценка: 2 (1)
Здравствуйте, pasenger, Вы писали:

P>Насчет "blah/details/get_black.h" интересно в принципе наверное.

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

ну не знаю... мне создавать файлы не обломно (болванки .hh/.cc генерятся GNU autogen'ом и остается только перенести в нее код) если хочется сохранить "чистоту" кода... документировать код из details хорошо, но не так важно как "публичный" код. я например когда усилено "кодю" просто помечаю все из details doxyhgenoвским @internal... да и вообще писать код и хорошие доки одновременно нужно терпение... обычно если код "прет", то лучше не останавливаться и хорошо документировать получется уже после того как все закодено/оттестировано ... и, если остается время (и есть желание ), я документирую то, что попало в details -- скорее для того, чтобы тот кто, ни дай Бог, полезет сюда зачемнить был +\- в курсе что к чему если это, вдруг, не оч тривиально...
Инициализация локальной статической переменной
От: pasenger  
Дата: 22.11.10 17:46
Оценка:
Хочется синглтон мейерса инициализировать не сходя с места. Допустим, нужен обьект, определяющий черный цвет. Нужно этот объект создать, инициализировать и присвоить в статистическую переменную.
IColorPtr get_black() {
  IColorPtr ret(CLSID_RgbColor);
  ret->SetRed(0);
  ret->SetGreen(0);
  ret->Blue(0);
  return ret;
}

void foo() {
...
  static const IColorPtr black_color = get_black();
...
}

Этот вариант мне не нравится тем, что где-то снаружи находится функция (get_black), которая вообще никого не касается снаружи, и засоряет окружающую среду. Можно сделать через локальный класс, скажем так
void foo() {
...
  struct {
    IColorPtr operator () () {
      IColorPtr ret(CLSID_RgbColor);
      ret->SetRed(0);
      ret->SetGreen(0);
      ret->Blue(0);
      return ret;
    }
  } black_color_wrap;
  static const IColorPtr black_color = black_color_wrap();
...
}

Вопрос состоит в том, можно ли вообще закрыть код по созданию black_color даже для области видимости внутри foo? Напишу пример, который не компилируется (более того, компилятор моей VS2005 падает), но который приблизительно показывает, что бы хотелось
void foo() {
...
  static const IColorPtr black_color = (struct {
    IColorPtr operator () () {
      IColorPtr ret(CLSID_RgbColor);
      ret->SetRed(0);
      ret->SetGreen(0);
      ret->Blue(0);
      return ret;
    }
  })(); // "}) ()();" ??
...
}

к сожалению, C++0x не доступно, т.е. никаких лямбд
Заранее спасибо
Re: Инициализация локальной статической переменной
От: Erop Россия  
Дата: 22.11.10 19:26
Оценка:
Здравствуйте, pasenger, Вы писали:

P>void foo() {
P>...
P>  static const IColorPtr black_color = get_black();
P>...
P>}


Конечно же да.
void foo() {
    static const IColorPtr blackColor = 0;
    if( blackColor == 0 ) {
        static IColorImpl blackColorImpl;
        blackColorImpl.SetOne();
        blackColorImpl.SetTwo();
        blackColorImpl.SetThree();

        blackColor = &blackColorImpl; 
    }
    // тут код использования blackColor.
}
только так делать стрёмно, так как обычно стараюстся код из if( blackColor == 0 ) наоборот вынести в отдельную функцию. Чисто чтобы не загромождать код foo() лишними подробностями.
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re[2]: Инициализация локальной статической переменной
От: pasenger  
Дата: 23.11.10 06:03
Оценка:
Здравствуйте, zaufi, Вы писали:

Z>мое imho в таких случаях: если foo() находится в .cpp то помещаем get_black() в анонимное пространство имен гденить выше, если же она в hpp, то помещаем в пространство имен details (заключенное в текущее пространство имен...). само имя details явно указывает что никто, исключая текущую библиотеку\подсистему\whatever не должен снаружи использовать сущьности из него...


Я тоже помещаю в таких случаях случаях функции в анонимный namespace. Но в результате получается куча функций, которые которые вызываются только в одном месте. А данная конкретная функция так и вовсе вызывается один раз. Это деструктурирует файл и ухудшает читаемость (на мой вкус)
Re[2]: Инициализация локальной статической переменной
От: pasenger  
Дата: 23.11.10 13:12
Оценка:
Здравствуйте, Erop, Вы писали:

E>
void foo() {
E>    static const IColorPtr blackColor = 0;
E>    if( blackColor == 0 ) {
...
E>    }
E>    // тут код использования blackColor.
E>}
только так делать стрёмно, так как обычно стараюстся код из if( blackColor == 0 ) наоборот вынести в отдельную функцию. Чисто чтобы не загромождать код foo() лишними подробностями.


Всё-таки const у вас лишний. Да, это тоже классический способ. Но мне не нравится лишнее сравнение с точки зрения производительности. Если foo дёргается очень часто, то лучше бы без него обойтись
Re[4]: Инициализация локальной статической переменной
От: pasenger  
Дата: 23.11.10 13:21
Оценка:
Здравствуйте, zaufi, Вы писали:

Z>Здравствуйте, pasenger, Вы писали:


P>>Здравствуйте, zaufi, Вы писали:


Z>>>мое imho в таких случаях: если foo() находится в .cpp то помещаем get_black() в анонимное пространство имен гденить выше, если же она в hpp, то помещаем в пространство имен details (заключенное в текущее пространство имен...). само имя details явно указывает что никто, исключая текущую библиотеку\подсистему\whatever не должен снаружи использовать сущьности из него...


P>>Я тоже помещаю в таких случаях случаях функции в анонимный namespace. Но в результате получается куча функций, которые которые вызываются только в одном месте. А данная конкретная функция так и вовсе вызывается один раз. Это деструктурирует файл и ухудшает читаемость (на мой вкус)


Z>выноси все это в отдельные файлики типа там blah/details/get_black.hh (и пространство имен blah::details) если уж так не хочется "загрязнять" файлы с реализацией... -- сам для себя решай что тебе больше подходит: плодить файлики или немножко сделать "нечитаемым" код...


Z>но в принципе ничо в этом страшного нет (и в том чтобы оставить и в том чтобы вынести ) -- посмотри вон на буст ну да... смотреть в его исходники без "взрыва мозга" могут не все подряд, но с другой стороны у них документация одна из лучших в опен соурсе (и практически избавляет от необходимости лазить по сорцам)... попробуй и ты стремиться в эту сторону ... смысле делать доки для своего кода такими, чтоб тому кто пользуется не нужно было лазить в исходники

Z>правда встает другая дилемма: хорошая doxygen документация также "загрязняет" код -- ну по крайней мере если не выыносить ее в отдельные файлы... что вобщем то я за свою практику встречал пару раз %)

Насчет "blah/details/get_black.h" интересно в принципе наверное.
Но вот, честно говоря, и хочется избежать всяких таких прыжков. Мне всего лишь нужна константа "черный цвет". Не думаю, что это стоит того, чтобы создавать файлы, документировать и т.п.
Re[3]: Инициализация локальной статической переменной
От: Erop Россия  
Дата: 23.11.10 13:37
Оценка:
Здравствуйте, pasenger, Вы писали:

P>Всё-таки const у вас лишний.

Да.

P>Да, это тоже классический способ. Но мне не нравится лишнее сравнение с точки зрения производительности. Если foo дёргается очень часто, то лучше бы без него обойтись

Ну эта проверка в любом случае будет. А явная или неявная -- дело десятое...
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re: Инициализация локальной статической переменной
От: sidorov18 США  
Дата: 24.11.10 07:40
Оценка:
Здравствуйте, pasenger, Вы писали:

P>
IColorPtr get_black() {
P>  IColorPtr ret(CLSID_RgbColor);
  ret->>SetRed(0);
  ret->>SetGreen(0);
  ret->>Blue(0);
P>  return ret;
P>}

P>void foo() {
P>...
P>  static const IColorPtr black_color = get_black();
P>...
P>}


Судя по всему у вас COM.
А со статикой проблем не возникает? Я так подозреваю — CoUninitialize вызывается раньше, чем деструктор IColorPtr?
Re[2]: Инициализация локальной статической переменной
От: pasenger  
Дата: 26.11.10 17:58
Оценка:
Здравствуйте, sidorov18, Вы писали:

S>Судя по всему у вас COM.

S>А со статикой проблем не возникает? Я так подозреваю — CoUninitialize вызывается раньше, чем деструктор IColorPtr?

Если проблемы возникают, то я об этом не знаю. Хотя, когда вы это сказали, кажется, что должны бы. Правильно ли я понимаю, что статиков com_ptr_t и CComPtr лучше не держать? А вы не знаете, какой-то workaround для таких случаев?
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.