Перейти к содержанию
    

Стили оформления программ на C/C++ и их применимость

В 30.12.2023 в 21:10, dimka76 сказал:

Значит MSVC и GCC что-то делают не так.

Может это вы "что-то делаете не так"?

Вышеприведённый код нормально компилится MSVC (v14.00.50727.762), а также IAR (v7.80.4) и Embarcadero C++ (v7.30).

Т.е. - все компиляторы, которыми пользуюсь в последнее время нормально его компилят. Без каких-либо варнингов или ошибок.

Какая именно версия MSVC у вас "не переваривает объявление переменных внутри case"?

В 30.12.2023 в 21:10, dimka76 сказал:

А может быть вы не поняли о чем я ?

switch(...)
{
  case ... :
    {
      intt32_t a = 0;
      .....
    }
}

А может это вы не поняли о чём шла речь? И какое отношение имеет ваш код к тому, о чём сами же писали выше?:

В 30.12.2023 в 18:26, dimka76 сказал:

Или в случае объявления переменной внутри case, без этих скобочек вообще не обойтись.

Сначала говорите об объявлении переменной. А теперь приводите код объявления переменной с одновременной её инициализацией. Вы разницу улавливаете?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

2 hours ago, jcxz said:

Странно... не думал, что здесь так много не умеющих написать примитивное объявление переменной.... 

int Tst1(int a, int *p)
{
  int r;
  switch (a) {
    case 0:
      int i0;
      i0 = p[0];
      r = a + i0;
      break;
    case 1:
      int i1;
      i1 = p[1];
      r = a * i1;
      break;
    case 2:
      int i2;
      i2 = p[2];
      r = a << i2;
  }
  return r;
}

Что именно в таком тривиальном коде вызвало столько вопросов???   :scratch_one-s_head:

А вот ещё пример (для полных гуру программирования)

#define SET_R(n) \
  int i0;        \
  i0 = p[n];     \
  r = a + i0;    \
  break;
int Tst1(int a, int *p)
{
   int r;
   switch (a) {
    case 0:
      SET_R(0)
    case 1:
      SET_R(1)
    case 2:
      SET_R(2)
  }
   return r;
}

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

4 часа назад, x893 сказал:

А вот ещё пример

В свиче такой дефайн прокатит, а вот в if() SET_R(0) уже нет)))  

Изменено пользователем mantech

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

31 minutes ago, mantech said:

В свиче такой дефайн прокатит, а вот в if() SET_R(0) уже нет)))  

 

По секрету: это и в switch не прокатит

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/2/2024 at 12:33 PM, jcxz said:

Сначала говорите об объявлении переменной. А теперь приводите код объявления переменной с одновременной её инициализацией. Вы разницу улавливаете?

А зачем ее объявлять без инициализации ? Все равно рано или поздно эта переменная должна быть инициализирована. 

И вы в своем примере следующей же строкой ее инициализируете.

Ну, разве только чтобы передать указатель на нее в функцию, где ей присвоится значение.

Ну, ладно. Вот такой пример

case SETIDLETIMEOUT_CMD:
  //{
  t_StdAnswer* p_StdAnswer;
  p_StdAnswer = (t_StdAnswer*)answ_buf;
  SetIdleTimeoutCmdHandler((t_SetIdleTimeoutCmd*)p_hdr, p_StdAnswer);
  uint32_t axis_cnt;
  axis_cnt = gsettings.get_common().AxisCount;
  send((uint8_t*)p_StdAnswer, (axis_cnt * sizeof(t_SetIdleTimeoutCmd)), addr, port);
  //}
  break;

В MSVC и GCC в режиме СРР проходит без ошибок.

А GCC в режиме Си выдает ошибку следующего содержания

Quote

error: a label can only be part of a statement and a declaration is not a statement

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

3 часа назад, x893 сказал:

По секрету: это и в switch не прокатит

 добавьте фигурных скобок и прокатит 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

25 minutes ago, dimka76 said:

А зачем ее объявлять без инициализации ? Все равно рано или поздно эта переменная должна быть инициализирована. 

И вы в своем примере следующей же строкой ее инициализируете.

Ну, разве только чтобы передать указатель на нее в функцию, где ей присвоится значение.

Ну, ладно. Вот такой пример

case SETIDLETIMEOUT_CMD:
  //{
  t_StdAnswer* p_StdAnswer;
  p_StdAnswer = (t_StdAnswer*)answ_buf;
  SetIdleTimeoutCmdHandler((t_SetIdleTimeoutCmd*)p_hdr, p_StdAnswer);
  uint32_t axis_cnt;
  axis_cnt = gsettings.get_common().AxisCount;
  send((uint8_t*)p_StdAnswer, (axis_cnt * sizeof(t_SetIdleTimeoutCmd)), addr, port);
  //}
  break;

В MSVC и GCC в режиме СРР проходит без ошибок.

А GCC в режиме Си выдает ошибку следующего содержания

 

Правильно gcc говорит. Но можно сделать, что бы и gcc не говорил.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/2/2024 at 10:52 PM, x893 said:

Правильно gcc говорит. Но можно сделать, что бы и gcc не говорил.

Еще раз прошу заметить, что GCC в Си так говорит.

В режиме СРР отмалчивается.

Я просто скобочки использую везде и в любом режиме. 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

30 минут назад, dimka76 сказал:

А зачем ее объявлять без инициализации ? Все равно рано или поздно эта переменная должна быть инициализирована. 

Вопрос был не про "зачем", а про "можно" или "нельзя".

Мой пример показывает что "можно".

30 минут назад, dimka76 сказал:

А GCC в режиме Си выдает ошибку следующего содержания

error: a label can only be part of a statement and a declaration is not a statement

Какую-то чушь ваш GCC несёт... Где там метка? Или вы этот код вырезали?

Видимо какой-то баг в GCC.  :unknw:

3 минуты назад, x893 сказал:

Правильно gcc говорит.

Правильно??? И где же метка, про которую он говорит?

 

ЗЫ: Кривой GCC. Не пользуйте просто.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

3 minutes ago, jcxz said:

И где же метка, про которую он говорит?

- Видите метку ?
- Нет.
- А она там есть.

Тяжело найти метку, елси она нписана белыми буквами на белой бумаге.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/2/2024 at 10:54 PM, jcxz said:

Какую-то чушь ваш GCC несёт... Где там метка? Или вы этот код вырезали?

Видимо какой-то баг в GCC.  :unknw:

case ...:

и есть метка.

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

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

1 час назад, dimka76 сказал:

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

В си вроде как переменные должны всегда объявляться в начале функции. Так что очевидно, что объявление переменных внутри case - это априори не для си.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

9 минут назад, jcxz сказал:

В си вроде как переменные должны всегда объявляться в начале функции. Так что очевидно, что объявление переменных внутри case - это априори не для си.

В с99 в любом месте.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 1/2/2024 at 10:54 PM, jcxz said:

Видимо какой-то баг в GCC.

тогда уж в стандарте - так можно только в c23

https://godbolt.org/z/qYxj6hfbz

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...