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

Вопросы по изучению Си

Дык в топике вроде речь идет о С? И если компилятор не поддерживает С99,то тогда без вариантов..
В начале блока { } можно объявлять хоть в до-ансишном K&R, у которого ещё прототипов функций не было, так что в данном случае именно

if( условие )
{
   uint32_t count;
   ***
}
else
{
  ***
}

или, к примеру, так

switch( aaa )
{
    case bbb:
    {
        uint32_t count;
        ***
    }
    break;
    case ccc:
    {
        float sum;
        ***
    }
    break;
}

и это должен нормально отработать любой компилятор.

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


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

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

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

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


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

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

 

Я привел ссылку на конкретную книгу где все по пунктам расписано. Наверное не сложно эту книгу найти и прочесть.

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


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

Я привел ссылку на конкретную книгу где все по пунктам расписано. Наверное не сложно эту книгу найти и прочесть.

Там анализ идет в первую очередь касательно удобочитаемости и большей вероятностью ошибится нежели вопрос оптимизации и быстродействия.

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


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

Не забудьте инициализировать переменную, т.е. должно быть как-то так

какие-то действия
if (условие) {
   uint32_t count = SOME_VALUE; // какое-то нужно Вам значение
   ***
}
else {
  ***
}

У Вас тут ошибки не закралось? Я хочу сказать, что за переделами if(){} не будет существовать такой переменной как count или будет использована переменная из глобальной области видимости.

Как дальше по тексту будет использоваться переменная count?

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


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

У Вас тут ошибки не закралось? Я хочу сказать, что за переделами if(){} не будет существовать такой переменной как count или будет использована переменная из глобальной области видимости.

Как дальше по тексту будет использоваться переменная count?

ну если быть точным то ситуация такая

uint32_t count;
какие-то действия
if( условие )
{
   *** (тут count используется)
}
else
{
  *** (тут count не используется)
}
***
(тут count не используется)

 

Ну я для себя ответ понял, переменные нужно делать максимально локальнее, за исключением циклов :)

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


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

Добрый день! или не день =) ... Влеплю сюда вопрос по Си++.

 

Не пойму как реализовать следующую идею:

Заводим класс клавиатуры, в котором описан метод(процедура) опроса клавиатуры, которая обновляет находящуюся в этом-же классе переменную - битовую маску нажатых клавиш. (сколько клавиш-столько бит)

 class MtxKeypad
{
private:
  volatile KeyMapType NewKeyMap;   //  считываемая в данный момент карта клавиш
public:
  volatile KeyMapType KeyMap;       // последняя считанная карта клавиш

  // typedef Mtx_Button<1,1> Key_1;        // !! эти строки относятся к вопросу сабжа
// typedef Mtx_Button<1,2> Key_2;        // тут объявляются все кнопки и их расположение (строка,столбец) 
// typedef Mtx_Button<2,1> Key_Enter;    
// typedef Mtx_Button<4,1> Key_Cancel; 

  void Scan() {  // метод опроса клавиатуры
// ....
      KeyMap=NewKeyMap;
// ....
  }
};

далее заводим шаблон класса отдельной кнопки, который умеет сообщать, нажата эта кнопка или нет:

template <int Col, int Row>
class Mtx_Button : public MtxKeypad
{
    //friend class MtxKeypad;    // это вот ХЗ надо тут или нет
private:
static const KeyMapType mask=(1UL<<(Row*5+Col));
public:
  inline uint8_t Pressed() {return (MtxKeypad::KeyMap & mask)!=0;}
};

И нужно использовать потом так:

int main()
{
    MtxKeypad Keys;
    Mtx_Button<4,1> Key_A;
    for(;;)
    {
        Keys.Scan();
        if(MtxKeypad::Key_1::Pressed()) pin2.Toggle();  // ошибка
        if(Key_A.Pressed()) pin2.Toggle();  // работает если добавить Key_A.Scan(); но тут отдельный объект с отдельными переменными - неправильно
    }
}

Так вот ВНИМАНИЕ ВОПРОС: как правильно описать классы, если мне надо чтоб дочерние объекты не копировали родительский метод и переменные, а пользовались ими, влияли на них.

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


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

Наследовать кнопку от клавиатуры - это, имхо, перебор:) Достаточно хранить в кнопке ссылку на клавиатуру.

Типа так:

// шаблон кнопки
template<int row, int col, typename matrix>
class button
{
private:
    matrix& m_;  // ссылка на клавиатуру
public:
    button(matrix& M): m_(M) {}
    bool pressed() { return m_.keymap & (row*5+col); }
};

// класс клавиатуры
class kbd
{
public:
    button<0, 0, kbd> Enter(this);
    void Scan();
}

void main()
{
    kbd Kbd;
    Kbd.Scan();
    if (Kbd.Enter.presed())
    {
    }
}

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


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

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

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


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

Хорошо, но тогда эти ссылки будут храниться в ОЗУ, а ето непозволительный оверхед! Если даже в классе кнопки ссылку обьявить как константу и задавать в конструкторе, компилятор всеравно ее пихает в ОЗУ.. :(

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


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

Если даже в классе кнопки ссылку обьявить как константу и задавать в конструкторе, компилятор всеравно ее пихает в ОЗУ.. :(
А что ему еще делать? Если клавиатура одна - делайте ее члены и функции-члены статическими в базовом классе. Если клавиатур у вас несколько - кнопка должна знать, к какой имеено обращаться. Значит, ей нужна переменная для хранения указателя или ссылки. Даже если этот указатель компилятор расположит во флеше (и таких указателей несколько, ведь клавиатур тоже несколько) - ему надо как-то эти указатели различать, значит он вынужден будет хранить в кнопке какие-то данные, позволяющие выбрать нужный указатель.

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


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

Встретил в исходниках такую вот конструкцию

#define putnstr(str,n)  do {            \
        printf ("%.*s", n, str);    \
    } while (0)

Почему использован цикл do-while ведь все-равно printf() один раз будет вызвано, как с ним, так и без него?

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


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

Встретил в исходниках такую вот конструкцию

#define putnstr(str,n)  do {            \
         printf ("%.*s", n, str);    \
     } while (0)

Почему использован цикл do-while ведь все-равно printf() один раз будет вызвано, как с ним, так и без него?

Такая конструкция применяется если в теле макроса более одной операции (в данном случае эта конструкция излишняя). Пример:

#define func(a) do { aa(a); bb(a); } while(0)
#define func2(a) { aa(a); bb(a); }

if (some) func(a); else blablabla(a); // Ok
if (some) func2(a); else blablabla(a); // Syntax error

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


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

do { aa(a); bb(a); } while(0)

Уже обсуждалось, поиск в помощь, сообщение от Сергея Борща было.

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


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

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

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

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

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

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

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

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

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

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