Skocz do zawartości

[C] Atmega8 - Zamiana int na string/char dla wyświetlacza LCD


Pomocna odpowiedź

Cześć, mógłby mi ktoś wytłumaczyć w jaki sposób można przekształcić jeden typ zmiennej na drugi? Konkretnie chodzi mi tutaj o przypadek przerobienia int na string/char abym mógł wyświetlić zawartość takiej zmiennej na wyświetlaczu LCD.

 

Link to post
Share on other sites

sprintf na pewno pomoże, jest to funkcja mająca duże możliwości konwersji różnych typów danych oraz formatowania tekstu, jednak jej użycie spowoduje spore zwiększenie rozmiaru kodu wynikowego (czyli zajętości FLASH), co w mniejszych mikrokontrolerach AVR może nie być bez znaczenia. Ponadto użycie tej funkcji może początkującemu programiście sprawić problem.

Jeśli chodzi tylko o prostą konwersję liczby całkowitej do ciągu znaków, osobiście proponowałbym funkcję itoa oferowaną przez avr-libc (plik nagłówkowy <stdlib.h>).

Przykład użycia:

#include <avr/io.h>
#include <stdlib.h>

// zmienna przechowująca konwertowaną liczbę
// jako ciąg znaków do wyświetlenia
char str[7];

// przykładowa funkcja wyświetlająca ciąg znaków
// (nie wiem jak nazywa się Twoja)
void lcd_wyswietl_string(char* s) {
    // tutaj kod funkcji
}

int main(void)
{
    int liczba = 173;
    
    // można najpierw konwertować 
    // ostatni argument (10) oznacza, że chodzi nam o system dziesiętny
    itoa(liczba, str, 10);
    // później wyświetlić
    lcd_wyswietl_string(str);
    
    // można też od razu przekazać wskaźnik na ciąg znaków
    // do funkcji wyświetlającej
    lcd_wyswietl_string( itoa(liczba, str, 10) );
    while (1) 
    {
        
    }
}

Typ int w avr-libc jest 16-bitowy, dlatego do konwertowania liczb większych od 32767 lub mniejszych od -32768 wymaga użycia funkcji ltoa.

  • Lubię! 2
Link to post
Share on other sites

Oba sposoby działają, dzięki za pomoc 🙂

Mam tylko jeszcze jedno drobne pytanie co do kodu, dlaczego w char str jest akurat 7? To ma jakieś większe znaczenie? Jeszcze nie ogarniam w pełni języka C także no.. 😅

Link to post
Share on other sites
9 godzin temu, Mike84 napisał:

Mam tylko jeszcze jedno drobne pytanie co do kodu, dlaczego w char str jest akurat 7? To ma jakieś większe znaczenie?

W celu dokonania konwersji na string potrzebne jest zarezerwowanie odpowiedniej ilości miejsca w pamięci RAM, w której funkcja itoa będzie mogła umieścić wynik operacji, czyli ciąg znaków. Każdy ciąg znaków w języku C musi kończyć się znakiem terminującym (bajt o wartości 0). Do tego potrzebne jest miejsce na 5 cyfr, co wynika z zakresu wartości, jakie może przyjmować zmienna typu int (jak napisałem wcześniej w przypadku AVR jest to wartość 16-bitowa), no i miejsce na znak minus w przypadku liczb ujemnych. To daje razem 7 znaków. Jest to taka wartość minimalna rozmiaru bufora gwarantująca poprawne działanie.

Jeśli zadeklarujesz tablicę o większym rozmiarze, to nic strasznego się nie stanie. Czasami tak się robi, kiedy np. chcemy wykorzystać tę samą tablicę jako bufor wyników działania innych funkcji operujących na ciągach znaków. Natomiast w przypadku zbyt małego rozmiaru tablicy, funkcja itoa może przekroczyć rozmiar bufora i nadpisać obszar pamięci, w którym mogą znajdować się inne zmienne. Dodam, że takie błędy mogą nie objawiać się od razu, tylko pojawić się w dalszej fazie rozwoju programu i mogą być kłopotliwe do  wykrycia, dlatego z tym rozmiarem bufora należy uważać.

Edytowano przez andrews
  • Lubię! 1
Link to post
Share on other sites

Napotkałem kolejny bardzo bliźniaczy problem 😅

W jaki sposób można przekonwertować float na char? Chciałbym wyświetlać ułamki na wyświetlaczu

Link to post
Share on other sites

@BelferekTak kontrolnie zapytam... wiesz oczywiście co trzeba zrobić, aby avr-libcowy sprintf obsługiwał liczby zmiennoprzecinkowe?

Polecam lekturę: https://www.nongnu.org/avr-libc/user-manual/group__avr__stdlib.html#ga060c998e77fb5fc0d3168b3ce8771d42

A przy okazji na temat całej rodzinki *printf z opisem ograniczeń: https://www.nongnu.org/avr-libc/user-manual/group__avr__stdio.html#gaa3b98c0d17b35642c0f3e4649092b9f1

 

  • Lubię! 1
Link to post
Share on other sites
1 minutę temu, Mike84 napisał:

tylko w tym przypadku on tutaj nie pomaga

Pomoże jak dodasz jeden tajemniczy parametr do linkera (link wyżej). Inna sprawa, że to bez sensu przy ATmega8 z jej potężną ilością pamięci...

 

Link to post
Share on other sites
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.

jlcpcb.jpg

jlcpcb.jpg

Produkcja i montaż PCB - wybierz sprawdzone PCBWay!
   • Darmowe płytki dla studentów i projektów non-profit
   • Tylko 5$ za 10 prototypów PCB w 24 godziny
   • Usługa projektowania PCB na zlecenie
   • Montaż PCB od 30$ + bezpłatna dostawa i szablony
   • Darmowe narzędzie do podglądu plików Gerber
Zobacz również » Film z fabryki PCBWay

Dołącz do dyskusji, napisz odpowiedź!

Jeśli masz już konto to zaloguj się teraz, aby opublikować wiadomość jako Ty. Możesz też napisać teraz i zarejestrować się później.
Uwaga: wgrywanie zdjęć i załączników dostępne jest po zalogowaniu!

Anonim
Dołącz do dyskusji! Kliknij i zacznij pisać...

×   Wklejony jako tekst z formatowaniem.   Przywróć formatowanie

  Dozwolonych jest tylko 75 emoji.

×   Twój link będzie automatycznie osadzony.   Wyświetlać jako link

×   Twoja poprzednia zawartość została przywrócona.   Wyczyść edytor

×   Nie możesz wkleić zdjęć bezpośrednio. Prześlij lub wstaw obrazy z adresu URL.

×
×
  • Utwórz nowe...

Ważne informacje

Ta strona używa ciasteczek (cookies), dzięki którym może działać lepiej. Więcej na ten temat znajdziesz w Polityce Prywatności.