Как сравнить 2 числа?
- Войдите на сайт для отправки комментариев
Чт, 16/01/2020 - 19:42
Имеется 2 числа,оба могут находиться в диапазоне от 880 до 1080,как их сравнить по разрядно?
например 2 десятичных числа-1011 и 1010,мы то отличие видим,что в разряде единиц цифры отличаются,а в разрядах десятков,сотен и тысяч одинаковые,а как программно определить равны ли разряды единиц,десятков,сотен и тысяч отличаются или нет?
Имеется 2 числа,оба могут находиться в диапазоне от 880 до 1080,как их сравнить по разрядно?
очевидно, что числа надо разбить на разряды - то есть 880 это будет 0-8-8-0, а 1080 -1-0-8-0 - и каждый разряд сравнить отдельно. Это и будет "поразрядно"
Сделал так,но работает не корректно
unsigned int freq=1011,freqOld=1010; byte c=0,d = 0; c = freqOld/ 1000;d = freq / 1000; if(c!=d){не равны разряд тысячных} c = ( freqOld% 1000 ) / 100;d = ( freq% 1000 ) / 100; if(c!=d){не равны разряд сотых} c = ( freqOld% 100 ) / 10;d = ( freq% 100 ) / 10; if(c!=d){не равны разряд десятых} c = freqOld% 10;d = freq% 10; if(c!=d){не равны разряд единиц}работает не корректно
а конкретнее?
Так вроде и сделал-разряды разбил,но!
1011 и 1010-показывает разницу,а вот 1010 и 1011-не показывает!мистика
Это мне надо для приемника на RDA5807 и дисплея ILI9341,частота на дисплее 880-1080 (точка искуственная),при перестройке частоты на 1 приходиться перерисовывать все значение частоты,например была 1011,стало 1010,это занимает много времени,быстрее понять в каком разряде изменилось значение и отрисовать только этот разряд,да и помех приему меньше
Вот подпрограмма вывода на дисплей-
void Frequence() { //Tft.drawNumber(freqOld, 0, 90, 12, BLACK);freqOld=freq; Tft.drawNumber(freq, 0, 90, 12, BLUE); unsigned int c=0,d = 0; //https://robotclass.ru/tutorials/arduino-dynamic-led-indication/ itoa(freq, buffer, 10);Tft.drawString(buffer, 60, 0, 5, BLUE); c = freqOld/ 1000;d = freq / 1000; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 0, 90, 12, BLACK);freqOld=freq;sprintf(buffer,"%01d",d);Tft.drawString(buffer, 0, 90, 12, BLUE);} c = ( freqOld% 1000 ) / 100;d = ( freq% 1000 ) / 100; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 80, 90, 12, BLACK);freqOld=freq;sprintf(buffer,"%01d",d);Tft.drawString(buffer, 80, 90, 12, BLUE);} c = ( freqOld% 100 ) / 10;d = ( freq% 100 ) / 10; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 160, 90, 12, BLACK);freqOld=freq;sprintf(buffer,"%01d",d);Tft.drawString(buffer, 160, 90, 12, BLUE);} c = freqOld% 10;d = freq% 10; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 240, 90, 12, BLACK);freqOld=freq;sprintf(buffer,"%01d",d);Tft.drawString(buffer, 240, 90, 12, BLUE);} freqOld=freq; }почему 1010 и 1011 не показывает разницы - не вижу, но в целом у вас в логике ошибка. Подумайте, как будет работать ваш код, если разница будет не в одной цифре, а в двух, например 1010 и 1009
если числа 1010 и 1009,то есть на экране частота 1010,и она сменилась на 1009,то как я хочу-
сравниваем тысячные-одинаковые,не перерисовываем
сравниваем сотые-одинаковые,не перерисовываем
сравниваем десятки-отличаются,стираем 1 и рисуем 0
сравниваем единицы-отличаются,стираем 0 и рисуем 9
XOR
Спасибо!нашел ошибку,лишние freqOld=freq; в сравнениях!!!
Вот так теперь
byte x; unsigned int freq=1011,freqOld=9999,c,d; void Frequence() { c = freqOld/ 1000;d = freq / 1000;x=0;if(c!=d){tft_razrjad();} c = ( freqOld% 1000 ) / 100;d = ( freq% 1000 ) / 100;x=80;if(c!=d){tft_razrjad();} c = ( freqOld% 100 ) / 10;d = ( freq% 100 ) / 10;x=160;if(c!=d){tft_razrjad();} c = freqOld% 10;d = freq% 10;x=240;if(c!=d){tft_razrjad();} freqOld=freq; } void tft_razrjad() { sprintf(buffer,"%d",c);//стираем число в разряде Tft.drawString(buffer,x, 90, 12, BLACK); sprintf(buffer,"%d",d);//пишем новое число в разряде Tft.drawString(buffer, x, 90, 12, BLUE); }Тему можно закрыть!еще раз огромное спасибо!
использование глобальных переменных внутри функции - плохой стиль
так?
void Frequence() { int c,d; //тестовое отображение частоты sprintf(buffer,"freq=%01d",freqOld );Tft.drawString(buffer, 60, 0, 4, BLACK);sprintf(buffer,"freq=%01d",freq );Tft.drawString(buffer, 60, 0, 4, BLUE); c = freqOld/ 1000;d = freq / 1000;x=0;if(c!=d){tft_razrjad(c,d);} c = ( freqOld% 1000 ) / 100;d = ( freq% 1000 ) / 100;x=80;if(c!=d){tft_razrjad(c,d);} c = ( freqOld% 100 ) / 10;d = ( freq% 100 ) / 10;x=160;if(c!=d){tft_razrjad(c,d);} c = freqOld% 10;d = freq% 10;x=240;if(c!=d){tft_razrjad(c,d);} freqOld=freq; } void tft_razrjad(int val0,int val1) { sprintf(buffer,"%d",val0);//стираем число в разряде Tft.drawString(buffer,x, 90, 12, BLACK); sprintf(buffer,"%d",val1);//пишем новое число в разряде Tft.drawString(buffer, x, 90, 12, BLUE); }Во-первых, так вообще работать не будет - buffer потеряли.
Ну и кроме того, касаемо стиля стало еще хуже - теперь в процедуре Frequence() куча глобальных параметров, описанных непонятно где и используемых "втемную". Уж лучше прежний вариант верните :)
Если надо сравнивать не числа, а символы в строке, то я бы так и поступил (хоть это и неизящно): законвертил два числа в две ASCIIZ строки и пробежался по ним циклом. Символ не совпадает - перерисовываем.
b707 по мне так в посте 5 для меня нагляднее,там норм?
void Frequence() {intc=0,d = 0;c = freqOld/ 1000;d = freq / 1000;if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 0, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 0, 90, 12, BLUE);} c = ( freqOld% 1000 ) / 100;d = ( freq% 1000 ) / 100; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 80, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 80, 90, 12, BLUE);} c = ( freqOld% 100 ) / 10;d = ( freq% 100 ) / 10; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 160, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 160, 90, 12, BLUE);} c = freqOld% 10;d = freq% 10; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 240, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 240, 90, 12, BLUE);} freqOld=freq; }b707 по мне так в посте 5 для меня нагляднее
ну и оставьте. Это я уже придираться стал. Главное работает
оставил так,еще раз спасибо!
void Frequence() { int c=0,d = 0; c = freqOld/ 1000;d = freq / 1000; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 0, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 0, 90, 12, BLUE);} c = ( freqOld% 1000 ) / 100;d = ( freq% 1000 ) / 100; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 80, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 80, 90, 12, BLUE);} c = ( freqOld% 100 ) / 10;d = ( freq% 100 ) / 10; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 160, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 160, 90, 12, BLUE);} c = freqOld% 10;d = freq% 10; if(c!=d){sprintf(buffer,"%01d",c);Tft.drawString(buffer, 240, 90, 12, BLACK);sprintf(buffer,"%01d",d);Tft.drawString(buffer, 240, 90, 12, BLUE);} freqOld=freq; }Мой вариант (для обдумывания):
void showFrequency(uint16_t _newFrequency) { static char oldFreqStr[0x06]; char newFreqStr[0x06]; uint8_t charNo = 0x00; uint16_t printPos = 0x00; snprintf(newFreqStr, sizeof(newFreqStr), "%5u", _newFrequency); while (newFreqStr[charNo]) { if (newFreqStr[charNo] != oldFreqStr[charNo]) { // .drawChar() is exist? Tft.drawChar(oldFreqStr[charNo], printPos, 90, 12, BLACK); Tft.drawChar(newFreqStr[charNo], printPos, 90, 12, BLUE); } printPos += 80; charNo++; } // char-to-char copy can be done in the while() loop memcpy(oldFreqStr, newFreqStr, sizeof(oldFreqStr)); }А у меня частоты тоже целыми хранятся, дак я их абычна так вывожу
из 870 - 1080 делает 87.0 - 108.0
А просто рисую точку и все,никаких лишних вычислений,каждый разряд имеет свое знакоместо на дисплее
А просто рисую точку и все,никаких лишних вычислений,каждый разряд имеет свое знакоместо на дисплее
В частном случае использования семисегментника для отображения - да, метод годный. Но не всегда используется семисегментник ;) И поэтому дополнительные вычисления делать приходится (например, шрифты могут использоваться пропорциональные, а не моноширинные).
А просто рисую точку и все,никаких лишних вычислений,каждый разряд имеет свое знакоместо на дисплее
В частном случае использования семисегментника для отображения - да, метод годный. Но не всегда используется семисегментник ;) И поэтому дополнительные вычисления делать приходится (например, шрифты могут использоваться пропорциональные, а не моноширинные).
какой семисегментник? вы тему читали? дисплей ILI9341! и зачем для точки выделять знакоместо 72*96 пикселей (шрифт 6*8 ,увеличение в 12 раз) пикселей мне не понятно...нарисовал искуственно точку и забыл
Tft.drawString(buffer, 80, 90, 12, BLUE);
какой семисегментник? вы тему читали? дисплей ILI9341! и зачем для точки выделять знакоместо 72*96 пикселей (шрифт 6*8 ,увеличение в 12 раз) пикселей мне не понятно...нарисовал искуственно точку и забыл
Tft.drawString(buffer, 80, 90, 12, BLUE);
В любом случае, семисегментник или нет - это частный случай. Шрифты - бывают разные. Например, в библиотеке UTFT - они моноширинные, в других библиотеках - есть пропорциональные. Во втором случае, "нарисованная искусственно" точка по фиксированным координатам, при использовании пропорционального шрифта - может вызвать эффект визуальной "разорванности". Именно поэтому я и написал - это конкретно частный случай, великолепно заточенный либо под семисегментник (моноширинный шрифт однозначно), либо - под моноширинный шрифт на TFT-дисплее.
Я чего-то не понимаю. Если есть желание сравнить два числа, то надо вычесть из одного другое. Если сравнивать по разрядно, то такая-же петрушка. Выделить разряды каждого и вычесть из одного другое.
Что же касается получения значения определённого разряда числа - то вот, навскидку, вариант, без кучи if и использования pow. Запустить можно здесь: http://cpp.sh/37krb
// Example program #include <iostream> #include <string> using namespace std; int getRank(int num, int rank) { int k = 1; for(int i=0;i<rank;i++) { k *= 10; } int k2 = k/10; if(!k2) { k2 = 1; } return num%k/k2; } int main() { int i1 = 1234; cout << getRank(i1,1) << '\n'; cout << getRank(i1,2) << '\n'; cout << getRank(i1,3) << '\n'; cout << getRank(i1,4) << '\n'; cout << getRank(i1,5) << '\n'; }Как посчитать кол-во разрядов числа - тоже мог бы подсказать, но из палаты не выпускают.
как не в дырочку? пост http://arduino.ru/forum/pesochnitsa-razdel-dlya-novichkov/kak-sravnit-2-chisla#comment-508117 ,это ваши семисегментники не в тему
не хотел вам грубить,просто вы достали с этой точкой,которая только у вас вызывает чувство "разорванности"
Извините!
как не в дырочку? пост http://arduino.ru/forum/pesochnitsa-razdel-dlya-novichkov/kak-sravnit-2-chisla#comment-508117 ,это ваши семисегментники не в тему
не хотел вам грубить,просто вы достали с этой точкой,которая только у вас вызывает чувство "разорванности"
Извините!
Строго говоря - я пишу не только для вас. В том числе и для людей, которые понимают, что контроллеров TFT-дисплеев - множество, а не только ILI9341. В том числе - для людей, которые понимают, что инструменты для вывода информации на дисплей, включая библиотеки и шрифты - могут использоваться разные. И именно поэтому я упомянул, что ваше решение - только частный случай, и объяснил, почему.
Если моя точка зрения вызывает у вас бугурт, то повторюсь - попейте новопассит. Но здесь я, также как и вы - имею полное право высказать свою точку зрения, и буду это делать независимо от того, какие такие слова и сентенции вас достают, и почему что-то странное и нехорошее происходит с вашей психикой. Надеюсь, я вполне доходчиво объяснил.
Еще возник вопрос,не по теме-тачскрину,здесь задавать или плодить еще темы?
Еще возник вопрос,не по теме-тачскрину,здесь задавать или плодить еще темы?
Какой контроллер тачскрина - для начала?
У меня только сама панель тачскрина от дисплея SPFD5408 ,без контроллера,в файле "TFTv2.h" есть строки-
Также в примере программы "POINT" есть библиотека "#include <SeeedTouchScreen.h>",ее я нашел https://github.com/Seeed-Studio/TFT_Touch_Shield_V2 ,будет ли работать? если заработает то можно отказаться от кнопок,тогда вообще будет красота!
Тач - резистивный, ничего не мешает попробовать, тем более - есть с чего начать. Вот тут нашёл статейку, там про ваш тачскрин, похоже: https://misc.ws/2013/11/08/touch-screen-shield-for-arduino-uno/
На форуме тоже мелькало: http://arduino.ru/forum/apparatnye-voprosy/deshevyi-tft-24-displei-na-spfd5408
Также похоже, что указанная вами библиотека от SeedStudio тоже подойдёт.
К сожалению ILI9341 с тачскрином и TSC2046 стоит в другом проекте,если здесь тач не заработает придется выдернуть оттуда контроллер
Попробую подключить тач без контроллера,спасибо!
Работает!!! огромное спасибо!
только подправил
Пока так,осталось добавить часы и термометр
(120 28 это координаты нажатия на тач,для отладки)