Tablica char na tablicę int.

0

Dzień dobry,
wysyłam na mikrokontroler przez UART wartości z zakresu 0-4000. Każda cyfra zapisywana jest na mikrokontrolerze w odpowiednim buforze.

char buffor[buffor_size];

Następnie te wartości chciałabym przekazać na przetwornik mikrokontrolera, który przyjmuje jedynie wartości Uint32_t. Jednak nie potrafię przekonwertować tablicy charakterów na tablicę intów. Wiem, że zmienna char jest 8 bitowa, to oznaczało by, że musze wziąć po 4 symbole(cyfry) z bufora char, by otrzymać zmienną 32 bitową. Jednak nie potrafię w Internecie znaleźć odpowiednich funkcji.

Czyli tablica char wyglądałaby na przykład tak:

char buffor[12] = '4', '0', '0', '0', '0', '0', '0', '2', '0', '4' ,'5' , '7';

A tablica int:

int buffor1[3] = {4000, 2, 456};

W przykładach w Internecie znalazłam głównie przykłady z char *buffor. Dlatego nie pasowałyby do przesyłanych informacji. Z góry dziękuję.

1

Oj nie, takich wartości by nie było w tej tablicy charów, aby otrzymać takie wartości intów.

Ogólnie od takich rzeczy jest memcpy, ale skoro piszesz na mikrokontrolery to może sie okazać, że masz słaby kompilator/bibliotekę standardową i trzeba będzie rozwiązać to w brzydki sposób.

W każdym razie, zakładając little-endian i 32-bitowy int:

char x[4] = { 0x01, 0x02, 0x03, 0x04 };
unsigned y;
memcpy(&y, x, sizeof(y));
assert(y == 0x04030201);

Jak widzisz podobieństwo widać w w wartościach heksadecymalnych; porównanie wartości dziesiętnych do wartości złożonych ze znaków nie ma sensu.

0

Tak wygląda mój buffor z wartościami przesłanymi na mikrokontroler.
Korzystam z STM32f303k8 i środowiska Keil v5.
Edytowałam załącznik: Jednak to przez błąd w transmisji, tak wygląda to poprawnie:

Capture.PNG

0

No spoko, zobacz jak wyjdzie z użyciem memcpy. Nie znam tego środowiska - zwróć uwagę czy przypadkiem wygenerowany kod maszynowy nie będzie okropny.

0

Gdy dochodzi do tej konwersji zmienne wyglądają jak w załączonych plikach.
W wejściowym 1 7 7 0 w y=3618609.

Jeszcze nadmienię, że tablica przyjmująca wartości nie będzie miała tylko 4 wartości, ale więcej, więc powinno się ją podzielić zawsze w równych odstępach po 4 symbole.

1

Czekaj, źle Cię zrozumiałem chyba i namieszałem.

Czy ty przesyłasz to jako 12-znakowy tekst? Wtedy faktycznie pierwszy przykład masz poprawnie-ish, a zamiany dokonuj po prostu jako odpowiednie mnożenia.

int char_buf_to_int(static char buf[4])
{
    int result = 0;
    result += (buf[0] - '0') * 1000;
    result += (buf[1] - '0') *  100;
    result += (buf[2] - '0') *   10;
    result += (buf[3] - '0') *    1;
    return result;
}

// ...

char input[4] = { '1', '2', '3', '4' };
int val = char_buf_to_int(input);

Powyższe zakłada, że zawsze są 4 znaki i że nie ma sensu robić z tego pętli, a tak być nie musi.

0

To może od początku.
Z pliku WAVE pobieram wartości chwilowe amplitudy, które później wysyłam na mikrokontroler, nie są to stałe wartości. To dałam w pierwszym załączniku.
Następnie przesyłam je na mikrokontroler do tablicy char mającej 200 indeksów. Chciałabym podzielić tę tablice char tak by każdy int składał się z 4 indeksów tablicy char. Ponieważ przesyłając wartość 2000, zapisywana jest ona w 4 kolejnych indeksach.
buffor[0]='2';
buffor[1] = '0';
buffor[2] = '0';
buffor[3] = '0';
A w dalszych indeksach też zapisywane są wartości.
.
.
.
buffor[197] = '0';
buffor[198] = '1';
buffor[199]='1';
buffor[200]='2';
Co chciałabym by dało tablicę intów. tab[]={2000,...,112};

1

Skoro bufor ma mieć 200 char-ów, to aby przemielić cały potrzebujesz:

for (int cnt = 0; cnt < 200; cnt += 4)//tutaj pułapka - wielkość int zależy od maszyny, na 64bitowych ma rozmiar 8 bajtów.
{
    int converted = (charBuffer[cnt] - '0') * 1000
    converted += (charBuffer[cnt + 1] - '0') * 100;
    converted += (charBuffer[cnt + 2] - '0') * 10;
    converted += charBuffer[cnt + 3] - '0';
    //i teraz tego skonwertowanego inta wsadzasz sobie do tablicy intów    
}
0
Cebulciax napisał(a):

Następnie przesyłam je na mikrokontroler do tablicy char mającej 200 indeksów. Chciałabym podzielić tę tablice char tak by każdy int składał się z 4 indeksów tablicy char. Ponieważ przesyłając wartość 2000, zapisywana jest ona w 4 kolejnych indeksach.

A w ilu indeksach jest zapisywana wartość 200? W jaki sposób?
Jeśli zapis pojedynczej liczby nie jest zawsze 4-cyfrowy to strona wysyłająca jest do przeróbki.

1
Cebulciax napisał(a):

To może od początku.
Z pliku WAVE pobieram wartości chwilowe amplitudy, które później wysyłam na mikrokontroler, nie są to stałe wartości. To dałam w pierwszym załączniku.
Następnie przesyłam je na mikrokontroler do tablicy char mającej 200 indeksów. Chciałabym podzielić tę tablice char tak by każdy int składał się z 4 indeksów tablicy char. Ponieważ przesyłając wartość 2000, zapisywana jest ona w 4 kolejnych indeksach.
buffor[0]='2';
buffor[1] = '0';
buffor[2] = '0';
buffor[3] = '0';
A w dalszych indeksach też zapisywane są wartości.
.
.
.
buffor[197] = '0';
buffor[198] = '1';
buffor[199]='1';
buffor[200]='2';
Co chciałabym by dało tablicę intów. tab[]={2000,...,112};

Jako, że nie wiadomo po co to robisz trudno zrozumieć o co chodzi, szczególnie, że opis wskazuje na jakieś bardzo dziwne zachowanie (nie brzmi ono znajomo i sensownie).
Możesz na chwilę zapomnieć jak chcesz to oprogramować i opisać funkcjonalność jaką ma wykonywać ten mikrokontroler?
Będzie łatwiej zrozumieć co zamierzasz i czy twoje zamiary są właściwe.
Np: "chcę mrugać diodami zależnie od natężenia dźwięku."

Czemu mnie niepokoi twój opis?

  • piszesz o dźwięku WAVE
  • grupujesz 4 znaki ASCII i chcesz zinterpretować je jako liczby dziesiętne co nijak się

Te dwie rzeczy zupełnie do siebie nie pasują i wskazują na to, że rozwiązanie jakiegoś problemu jest nieprawidłowe, albo opis niekompletny.

0
MasterBLB napisał(a):

Skoro bufor ma mieć 200 char-ów, to aby przemielić cały potrzebujesz:

for (int cnt = 0; cnt < 200; cnt += 4)//tutaj pułapka - wielkość int zależy od maszyny, na 64bitowych ma rozmiar 8 bajtów.
{
    int converted = (charBuffer[cnt] - '0') * 1000
    converted += (charBuffer[cnt + 1] - '0') * 100;
    converted += (charBuffer[cnt + 2] - '0') * 10;
    converted += charBuffer[cnt + 3] - '0';
    //i teraz tego skonwertowanego inta wsadzasz sobie do tablicy intów    
}

Dziękuję, właśnie o takie coś chodziło.

Jeśli chodzi o przyczynę takiego pytania to śpieszę z odpowiedzią.
Chcę zrobić wzmacniacz audio, który będzie komunikował się z komputerem przez Bluetooth, jako, że przez UART można przesłać tylko 8-bit char, a do przetwornika cyfrowo-analogowego 32bit uint, po przesłaniu musze zrobić konwersję jednego z typów na drugi. Chciałam pominąć, przez moją małą wiedzę z zakresu programowania, odczytywanie wartości pliku WAVE. Dlatego najpierw konwertuję go na komputerze na chwilowe wartości amplitudy, a następnie wysyłam te wartości na mikrokontroler. Może niezbyt elegancka praktyka, ale z moja wiedzą, jedyna możliwa do zrealizowana.
Dziękuję wszystkim za odpowiedzi.

Liczba 200 zapisywana jest w sposób '0', '2' ,'0','0'. Więc zawsze z 4 elementów char, chciałam robić jedną wartość int.

0

Dzień dobry,
Próbowałam poradzić sobie z problemem włożenia tych danych do tablicy jednak chyba sobie nie radzę.

Stworzyłam tablicę intów, a nastęnie chciałam je zapisać za pomocą pętli.

for(int i=0; t<buffor_size;i++){
convertedTab[i]=converted;}

Czy jest to słuszny sposób? Wartości w ten sposób cały czas się nadpisują.

0

Przydałoby się trochę więcej kontekstu.

0

Gdy wysyłam dane do mikrokontrolera odbieram je w przerwaniu, a gdy transmisja się skończy zapisuję w danej tablicy char. Następnie wartości są konwertowane na tablicę int. Niestety ta wartość się nadpisuje, co powoduje, że i tablica się nadpisuje, a chciałabym, by była statyczna.
Jeśli wyzerowałabym tablicę char, która przychodzi do mikrokontrolera zmienna converted przyjmuje minusową wartość -53328 i wypełnia nią całą tablicę intów. A chciałabym, by ta tablica została zapisana tylko raz.

1 użytkowników online, w tym zalogowanych: 0, gości: 1