Stránka 1 z 1
xc8+pic - for nezastaví na nule
Napsal: 18 úno 2017, 16:41
od dracekvo
Ahoj,
může mi někdo prosím vysvětlit, proč když udělám v xc8 a pic 16f88 toto
bit_to_lcd(unsigned char a)
{
char b;
for(b=7;b>=0;b--) {
if((a & (1<<b))!= 0) {
lcd_zapis("1");
} else {
lcd_zapis("0");
}
}
}
tak prostě for jede furt do nekonečna.
Aby to fungovalo, tak musím udělat odčítání od 8 do 1
for(b=8;b>0;b--) {
a pak v podmínce od b odečítat 1
if((a & (1<<b-1))!= 0) {
opravdu nechápu, proč nezastaví.
Napsal: 18 úno 2017, 16:52
od Atlan
Pozeram ze tvoje myslenie je komplikovane pre 8bit uP. Nechces to napisat jednoduchsie? Napr s vyuzitim bitoveho posunu? Teda ak som vobec s kopy tych operatorov pochopil co mas v umysle.
C=0b1000 0000;
Bcko daj normalne. For b=0 b<7; b++
(
If (a&c) posli 1 else posli 0;
C>>1;
)
Napsal: 18 úno 2017, 18:34
od dracekvo
Ten if sem někde ukradl. Mě to moc nejde na mozek pracovat ve vyšším jazyce s bitama.
Má to být věc, co mi na LCD vypíše obsah charu bitově.
Tj 3 mi zobrazí jako 00000011.
b jsem dal obrázeně, protože mi ho to vypisovalo pozpátku 11000000.
tvůj příklad zkusím zítra implementovat. Děkuji
Napsal: 18 úno 2017, 18:56
od mtajovsky
Mě to funguje. Vypadá to, že váš překladač bere char b jako unsigned. Když se pak b dekrementuje z nulové hodnoty tak se výsledek nebere jako -1, ale jako 127. Pokud chcete zachovat funkci v podobném tvaru, tak bych použil méně využívaný cyklus do-while, který programátoři pohříchu opomíjejí:
Kód: Vybrat vše
void bit_to_lcd1(unsigned char a)
{
char b = 7;
do
{
if((a & (1<<b))!= 0)
{
lcd_zapis("1");
}
else
{
lcd_zapis("0");
}
}while(b-- != 0);
}
Napsal: 19 úno 2017, 08:48
od Programator
Typ char je maličko odlišný od ostatních intergrálních typů - char, signed char a unsigned char jsou tři odlišné typy, přitom je nespecifikováno zdali je typ char znaménkový nebo ne a každý kompilátor to může mít podle toho, jak se autor vyspal. To je i tento případ. Kompilátor tazatele má char unsigned, a kompilátor p. mtajovského signed. Řešením je buď počítat od 8, nebo změnit typ na signed char.
Pozn.: Jako profesionální programátor musím říct, že je pravda, že se cyklu do-while vyhýbám, stejně jako drtivá většina ostatních programátorů, ale ono to má svoje důvody - čitelnost, přehlednost, korektnost apod. Ale to by bylo na delší diskuzi (čti flamewar).
Napsal: 19 úno 2017, 09:19
od lesana87
V SDCC pro Z80 mi vychází nejkratší kód při použití for a ternárního operátoru, volání lcd_zapis je ve výsledném asm jen jednou. Při použití if se lcd_zapis volá dvakrát. Ale to asi bude závislé od chytrosti překladače.
Kód: Vybrat vše
void bit_to_lcd1(unsigned char a)
{
unsigned char b;
for (b = 0b10000000; b > 0; b >>= 1) {
lcd_zapis(a & b ? "1" : "0");
}
}
Napsal: 21 úno 2017, 19:02
od Jenda_KL
dracekvo píše:for(b=7;b>=0;b--)
protože for (init; podmínka; akce).
Podmínka b>=0 je splněna vždy. Po podtečení (b==255) je splněna taktéž.
edit: Jsem nečetl celé, vidno bylo toto, což mě taky nachytalo.