реклама на сайте
подробности

 
 
5 страниц V  < 1 2 3 4 > »   
Reply to this topicStart new topic
> Cpp check ругается, можно ли так писать?
x893
сообщение Feb 6 2018, 14:26
Сообщение #16


Профессионал
*****

Группа: Свой
Сообщений: 1 333
Регистрация: 27-10-08
Из: Планета Земля
Пользователь №: 41 226



Цитата(jcxz @ Feb 6 2018, 17:19) *
Нет. Не понимаю каким боком относится приведённый пример к Вашему вопросу.

Пример никак к теме не относится.
Но судя по высказываниям - ожидается большая дискуссия между гуру программирования.
Начинающие начинают попкорн готовить.
Go to the top of the page
 
+Quote Post
ViKo
сообщение Feb 6 2018, 14:30
Сообщение #17


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(x893 @ Feb 6 2018, 17:26) *
Пример никак к теме не относится.
Но судя по высказываниям - ожидается большая дискуссия между гуру программирования.
Начинающие начинают попкорн готовить.

Так, жду-с.
Вот здесь чего-то пишут, но не могу понять.
http://en.cppreference.com/w/cpp/language/eval_order
Go to the top of the page
 
+Quote Post
Сергей Борщ
сообщение Feb 6 2018, 14:36
Сообщение #18


Гуру
******

Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095



QUOTE (ViKo @ Feb 6 2018, 16:30) *
Так, жду-с.
Вам уже дали правильный и исчерпывающий ответ:
QUOTE (_pv @ Feb 6 2018, 15:34) *
а может всё-таки сначала инкрементируете, потом считаете логарифм уже от следующего элемента, но результат записываете на место предыдущего?
Компилятор имеет на это полное право. Чего еще вы ожидаете услышать?


--------------------
На любой вопрос даю любой ответ
"Write code that is guaranteed to work, not code that doesn’t seem to break" (C++ FAQ)
Go to the top of the page
 
+Quote Post
ViKo
сообщение Feb 6 2018, 14:39
Сообщение #19


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(Сергей Борщ @ Feb 6 2018, 17:36) *
Вам уже дали правильный и исчерпывающий ответ:
Компилятор имеет на это полное право. Чего еще вы ожидаете услышать?

Здесь тоже сначала инкрементируют, потом записывают?
while (*s++ = *t++)
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Feb 6 2018, 14:41
Сообщение #20


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



QUOTE (ViKo @ Feb 6 2018, 20:34) *
Точно, так нельзя писать? w00t.gif

Я бы избегал подобных неоднозначностей. Лучше записать код длинне на пару строк, но так, чтобы его понял любой компилятор/транслятор/синтезатор и статический анализатор. А самое главное - вы сами через пару-тройку лет, или другой коллега))))

Кстати, свои произведения проверяю также CppCheck и встроенным в IAR анализатором. Иногда помогает устранить весьма абсурдные и детские ошибки, допущенные по невнимательности.


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Feb 6 2018, 14:43
Сообщение #21


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(ViKo @ Feb 6 2018, 16:39) *
Здесь тоже сначала инкрементируют, потом записывают?
while (*s++ = *t++)

Здесь у Вас два разных указателя. А значит - нет неопределённости по операциям постинкремента.
Если конечно у Вас в неких "первых строках", которые Вы не посчитали нужным привести здесь, не записано:
#define t s
biggrin.gif
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Feb 6 2018, 14:44
Сообщение #22


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



QUOTE (ViKo @ Feb 6 2018, 22:39) *
Здесь тоже сначала инкрементируют, потом записывают?
while (*s++ = *t++)

Здесь всё в порядке, т.к. справа и слева от оператора присвоения у вас разные переменные, и они не зависят от друг друга.


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
SSerge
сообщение Feb 6 2018, 14:44
Сообщение #23


Профессионал
*****

Группа: Свой
Сообщений: 1 719
Регистрация: 13-09-05
Из: Novosibirsk
Пользователь №: 8 528



Цитата(ViKo @ Feb 6 2018, 21:30) *
Так, жду-с.

Извольте.
Стандарт С явно указывает что порядок вычисления левой и правой частей оператора присваивания не определён.
Цитата
6.5.16 Assignment operators:
4. The order of evaluation of the operands is unspecified.

А в С++ понаписали такого что и с бутылкой не разберёшь.

Так что да, по крайней мере в С, никто не гарантирует что pSigRe во время вычисления правой части не окажется уже инкрементирован в результате случившегося раньше вычисления левой части оператора присваивания.




--------------------
Russia est omnis divisa in partes octo.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Feb 6 2018, 14:45
Сообщение #24


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(ViKo @ Feb 6 2018, 16:22) *
Ладно. Значит, нужно найти точное толкование, когда инкрементируется указатель, если он используется справа и слева от оператора присваивания.

Это - на усмотрение компилятора/оптимизатора. Как ему удобнее.
Вобщем случае он может вообще никак не инкрементироваться в теле цикла, а только в его конце.
Или вообще цикл может быть развёрнут оптимизатором в линейный код. А все инкрементные и декрементные адресации заменены на адресации по указателю с фиксированным смещением.
А при следующей перекомпиляции с другими исходными условиями - не развёрнут, оставлен цикл.
Go to the top of the page
 
+Quote Post
haker_fox
сообщение Feb 6 2018, 14:46
Сообщение #25


Познающий...
******

Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125



Первый пример я бы записал так:
CODE
  for (uint32_t i = FFT_N; i--; ) {
    VarType_t result = log2f(*pSigRe) * 15.0515;
    *pSigRe++ = result;
  }

Ну для красоты result можно за цикл вынести, чтобы при каждой итерации не вызывать её конструктор (инициализатор).


--------------------
Выбор.
Go to the top of the page
 
+Quote Post
ViKo
сообщение Feb 6 2018, 14:57
Сообщение #26


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(SSerge @ Feb 6 2018, 17:44) *
Извольте.
Стандарт С явно указывает что порядок вычисления левой и правой частей оператора присваивания не определён.
А в С++ понаписали такого что и с бутылкой не разберёшь.
Так что да, по крайней мере в С, никто не гарантирует что pSigRe во время вычисления правой части не окажется уже инкрементирован в результате случившегося раньше вычисления левой части оператора присваивания.

Благодарствую! Хотя к чему такая толерантность. Мода laughing.gif
А вот Кейл с --remarks на строку
*pSigRe++ = log2f(*pSigRe) * 15.0515;
даже не заикнулся.

Буду смотреть, что он накомпилировал. Позже. Сейчас покидаю дискуссию.

Цитата(jcxz @ Feb 6 2018, 17:45) *
Вобщем случае он может вообще никак не инкрементироваться в теле цикла, а только в его конце.

Это уж дудки. В каждой операции цикла сделает все, что приказали.
Go to the top of the page
 
+Quote Post
Сергей Борщ
сообщение Feb 6 2018, 15:48
Сообщение #27


Гуру
******

Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095



QUOTE (ViKo @ Feb 6 2018, 16:57) *
Это уж дудки. В каждой операции цикла сделает все, что приказали.
Вас ждет еще много открытий в жизни. Посмотрите листинги своих программ повнимательнее.


--------------------
На любой вопрос даю любой ответ
"Write code that is guaranteed to work, not code that doesn’t seem to break" (C++ FAQ)
Go to the top of the page
 
+Quote Post
Arlleex
сообщение Feb 6 2018, 15:54
Сообщение #28


Местный
***

Группа: Участник
Сообщений: 492
Регистрация: 12-11-11
Пользователь №: 68 264



Довольно интересная тема в Си, связанная с базовым понятием точки следования.
Код
while (*s++ = *t++)

В конце условия стоит точка следования, а тем более, переменные разные, результат будет всегда одинаковым.
В конструкциях
Код
i = i++;

нет ни одной точки следования, кроме завершающей точки с запятой, поэтому результат не определен, выполнение приводит к undefined behavior.

Гуглите "sequence ponts in C". Например, тут.
Go to the top of the page
 
+Quote Post
jcxz
сообщение Feb 6 2018, 16:33
Сообщение #29


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(ViKo @ Feb 6 2018, 16:57) *
Это уж дудки. В каждой операции цикла сделает все, что приказали.

Он может даже количество итераций сделать не такое как Вы указали - например: объединить каждую чётную и нечётную итерации в одну, уменьшив их число в 2 раза. Может разбить цикл на два: в одном цикле объединить итерации попарно, в другом - выполнять по одной.
И ещё много чего может. Попробуйте как-нить включить максимальную оптимизацию.

Цитата(Сергей Борщ @ Feb 6 2018, 17:48) *
Вас ждет еще много открытий в жизни. Посмотрите листинги своих программ повнимательнее.

Я думаю, что ViKo никогда ещё не включал оптимизацию. И не заглядывал при этом в асм biggrin.gif
Go to the top of the page
 
+Quote Post
Den64
сообщение Feb 6 2018, 16:41
Сообщение #30


Знающий
****

Группа: Свой
Сообщений: 584
Регистрация: 22-11-07
Из: Курская область
Пользователь №: 32 571



Цитата(ViKo @ Feb 6 2018, 15:34) *
Имею массив из float и указатель на него.

Код
  pSigRe = SigRe;
    *pSigRe++ = log2f(*pSigRe) * 15.0515;

Точно, так нельзя писать? w00t.gif

Должно выполняться по порядку:
1. (*pSigRe)
2. log2f()
3. pSigRe++
4. *pSigRe
5. умножение
6. присвоение.
ИМХО так делать можно, компилятор не должен ругаться.
Go to the top of the page
 
+Quote Post

5 страниц V  < 1 2 3 4 > » 
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 16th June 2025 - 02:59
Рейтинг@Mail.ru


Страница сгенерированна за 0.01524 секунд с 7
ELECTRONIX ©2004-2016