Easyelectronics.ru

Электроника для всех
Текущее время: 23 сен 2020, 09:36

Часовой пояс: UTC + 5 часов



JLCPCB – Прототипы печатных плат за $2/5шт. два слоя. $5/5шт. четыре слоя
Крупнейший производитель печатных плат и прототипов. Более 600000 клиентов и свыше 10000 заказов в день!
Получите скидку на почтовую отправку при первом заказе в JLCPCB!

Начать новую тему Ответить на тему  [ Сообщений: 29 ]  На страницу 1, 2  След.
Автор Сообщение
 Заголовок сообщения: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 00:18 
Старожил
Аватара пользователя

Зарегистрирован: 28 мар 2012, 10:33
Сообщения: 1229
Откуда: Сочи
У меня тут вопрос по языку C.

Как обычно, возникла идейка.
Имеется вот такая конструкция
Код:
const unsigned int ParamNumber[4] =
{
   4,
   10,
   315,
   321
};

Таких массивов несколько, в них хранятся наборы параметров.

Идея заключается в том, чтобы сделать switch в таком стиле:
Show

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

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

Так вообще можно делать, или нужна жесткая константа в каждом case?


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 00:47 
Старожил

Зарегистрирован: 15 янв 2013, 13:24
Сообщения: 5665
А скомпилировать было влом? Минута на эксперимент - и полУчили бы ценный опыт. Компилятор бы обругался и послал в отослал к описанию формата case в учебнике по Си.

Выражение в switch(...) может содержать переменные. Выражение в case(...) должно быть константным.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 00:58 
Старожил
Аватара пользователя

Зарегистрирован: 28 янв 2010, 20:18
Сообщения: 591
Смысл не очень понятен, индексом массива не пользуетесь же, везде статически задан. Код switch не всегда бывает оптимален по скорости выполнения, если Вам это нужно, вручную можно лучше сделать. В показанном примере можно проверять переменную counter на равенство только одному элементу ParamNumber, как только будет равен делать, что требуется и дальше проверять только со следующим элементом ParamNumber. Итого будет одно сравнение вместо switch.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 01:04 
Старожил

Зарегистрирован: 25 фев 2011, 18:45
Сообщения: 3685
Откуда: Новосибирск
Каждый case - это константа.
Show


Нахер всю конструкцию.
Код:
   Param1 = Param1Array[counter];
   Param2 = Param2Array[counter];


Последний раз редактировалось demiurg1978 27 мар 2016, 01:13, всего редактировалось 3 раз(а).

Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 01:07 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
Наборы параметров известны на этапе компиляции?
Если да - можно попытаться разрулить всё через макросы (я недавно как раз описывал один из типовых трюков).

Но в вашем примере с синхроимпульсами case не нужен. Вам каждый раз нужно сравнивать только с одним номером - следующим. Так что индекс в массиве и один if хватит.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 01:50 
Старожил
Аватара пользователя

Зарегистрирован: 28 мар 2012, 10:33
Сообщения: 1229
Откуда: Сочи
Нет, надо по всему первому массиву пробежать, если хотя бы один равен, подставить параметры из остальных, если нет- дефолтный параметр.
Да, через макросы удобно сделать.
Хотя и цикл можно, чтобы по первому массиву пробежался.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 01:54 
Старожил

Зарегистрирован: 25 фев 2011, 18:45
Сообщения: 3685
Откуда: Новосибирск
antonluba писал(а):
...

Напишите четко и подробно, с наглядным примером, что вам нужно. Подумаем.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 02:05 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
А как это у вас строки идут в произвольном порядке, что по всему массиву бегать надо?
И как это "хотя бы один равен"? Либо один, либо ни одного.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 03:29 
Заглядывает иногда
Аватара пользователя

Зарегистрирован: 28 мар 2014, 21:43
Сообщения: 61
можно если, объявить как
constexpr unsigned int ParamNumber[4] =

только это уже C++, -std=gnu++11


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 03:48 
Старожил
Аватара пользователя

Зарегистрирован: 04 окт 2011, 10:19
Сообщения: 2061
Нужно взять Дракон, нарисовать красиво и потом сгенерировать программу.
Получится быстро, красиво и наглядно.
И книг можно не читать.
Совсем.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 11:04 
Старожил
Аватара пользователя

Зарегистрирован: 28 мар 2012, 10:33
Сообщения: 1229
Откуда: Сочи
Нужно, когда счетчик достигает значения какого-либо элемента первого массива, параметрам присваивались значения, соответствующие индексу этого элемента массива. Параметры для этого записываются в другие массивы под соответствующими индексами.

Например. На 4 шаге синхронизации (элемент первого массива) нужно установить длинный синхроимпульс и половинный период, на 10 (второй эл-т) - обычный синхроимпульс и полный период и т.д.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 12:33 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
Примерно так:
Код:
static int next_event=0;
// и в цикле:
counter++;
if(counter==ParamNumber[next_event] {
  Param1 = Param1Array[next_event];
  Param2 = Param2Array[next_event];
  next_event++;
  if(next_event==4) next_event=0;
}


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 13:15 
Заглядывает иногда
Аватара пользователя

Зарегистрирован: 28 мар 2014, 21:43
Сообщения: 61
можно эти константы объявить enum'ом, зачем тут массив?


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 14:28 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
tehday, в смысле, в исходном коде топикстартера? Там да, логично.
Но лучше убрать switch вообще.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 14:33 
Заглядывает иногда
Аватара пользователя

Зарегистрирован: 28 мар 2014, 21:43
Сообщения: 61
согласен, так покомпкактней будет


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 20:23 
Старожил

Зарегистрирован: 25 фев 2011, 18:45
Сообщения: 3685
Откуда: Новосибирск
Код:
#define QUANT_PARAMETERS 4

const unsigned int ParamNumber[QUANT_PARAMETERS] =
{
   4,
   10,
   315,
   321
};

for (u08 i = 0; i < QUANT_PARAMETERS; i++)
{
   if (counter == ParamNumber [i])
   {
      // необходимые действия и выход из цикла.

     Param1 = Param1Array [counter];
     Param2 = Param2Array [counter];

      break; // просто выход из цикла for
      // или
      return; // выход из функции. зависит от программы.
   }
}



Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 21:44 
Старожил
Аватара пользователя

Зарегистрирован: 28 мар 2012, 10:33
Сообщения: 1229
Откуда: Сочи
Цикл слишком длинный получается.
С учетом того, что это последовательность, а не случайные значения, вариант aamonster подходит.
Но, похоже, на практике (после попытки написать и отладить такой код) останется case и жесткие константы.
Спасибо всем.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 22:42 
Старожил

Зарегистрирован: 25 фев 2011, 18:45
Сообщения: 3685
Откуда: Новосибирск
Ваше дело. Пробуйте варианты.
Show


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 23:04 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
demiurg1978, кстати, проверяли разницу кода между первым и вторым вариантом? Лет 15 назад я бы поставил на то, что второй быстрее, а сейчас уже не уверен, что там компилятор наоптимизирует (и даже не смотрю, т.к. на pc и маках bottleneck практически никогда не бывает в числодробилке).


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 23:17 
Старожил

Зарегистрирован: 25 фев 2011, 18:45
Сообщения: 3685
Откуда: Новосибирск
aamonster писал(а):
demiurg1978, кстати, проверяли разницу кода между первым и вторым вариантом? Лет 15 назад я бы поставил на то, что второй быстрее, а сейчас уже не уверен, что там компилятор наоптимизирует (и даже не смотрю, т.к. на pc и маках bottleneck практически никогда не бывает в числодробилке).

Конечно я проверил все варианты в дизассемблере. Автор балуется с формированием видеосигнала. А это требует скорости.
Такой способ собственной оптимизации на уровне си я применяю уже давно. Если вы знаете ассемблер и проанализируете сишный код и дизассемблер, то поймете.
Но как мне сказали, такой способ не на всех мк работает. Так как у многих мк нет аппаратных указателей.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 27 мар 2016, 23:52 
Старожил

Зарегистрирован: 17 дек 2014, 04:38
Сообщения: 705
Доброго времени суток !

Я так понял у Вас есть 5 вариантов функций, которые нужно выполнять при совпадении счетчика с элементом массива. Делается это несколько по другому:
Код:
const uint8_t arr[4]={4,55,88,121};
void myf1(int i);
void myf2(int i);
void myf3(int i);
void myf4(int i);
void myf5(int i);

void (*myfunc[5])(int i);

// инициализация
   myfunc[0] = &myf1;
   myfunc[1] = &myf2;
   myfunc[2] = &myf3;
   myfunc[3] = &myf4;
   myfunc[4] = &myf5;

// а далее проверка счетчика
for (i=0;i<4;i++)
     {
     if (count == arr[i]) myfunc[i](arr[i]);
     }


как то так. И быстродействие будет зависеть только от перебора вашего массива.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 28 мар 2016, 00:08 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
Недавно познакомились с указателями на функции, да? "Человеку, у которого в руках молоток, любая проблема кажется гвоздём".


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 28 мар 2016, 00:41 
Старожил

Зарегистрирован: 17 дек 2014, 04:38
Сообщения: 705
Ну, как недавно ? Лет 25 назад. В данной ситуации мне кажется это наиболее оптимальное решение. Но совершенству нет предела - можете предложить свое решение.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 28 мар 2016, 00:50 
Старожил

Зарегистрирован: 19 мар 2013, 19:37
Сообщения: 2795
Откуда: Санкт-Петербург
void1509, просто тут указатели на функции - чистый оверхед (а вы их ещё применили для самого медленного из вариантов решения, требующего просмотра всего массива каждый раз).
Вот если бы эти функции выполняли разные действия, а не различались только константами - тогда да.


Вернуться к началу
 Профиль  
 
 Заголовок сообщения: Re: Использование SWITCH-CASE на С
СообщениеДобавлено: 28 мар 2016, 01:19 
Старожил

Зарегистрирован: 17 дек 2014, 04:38
Сообщения: 705
почему же медленный ? Давайте рассмотрим первый пост. Топикстартер приводит код где происходит сравнения с каждым элементом массива. Для каждого элемента есть свои отличающиеся действия. То есть сравнения с каждым элементом массива не избежать, а массив указателей на функцию позволяет сократить код. К тому же подобное решение может обрабатывать произвольное количество элементов массива.

ЗЫ: Я кажется понял в чем ваше замечание - у топикстартера просто присваивание в соответствии с элементом массива, а я предложил универсальное решение, которое в данном случае избыточно.


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 29 ]  На страницу 1, 2  След.


Часовой пояс: UTC + 5 часов


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  

Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
Русская поддержка phpBB