Elektroda.pl
Elektroda.pl
X
CControls
Proszę, dodaj wyjątek www.elektroda.pl do Adblock.
Dzięki temu, że oglądasz reklamy, wspierasz portal i użytkowników.

konwersja Char array na String, ESP8266, wysyłka do ThingSpeak

labo 05 Gru 2018 20:17 1605 128
  • #31 05 Gru 2018 20:17
    LChucki
    Poziom 18  

    khoam napisał:
    Co do wyższości C nad C++, to ktoś kiedyś ładnie napisał, że "programiści C krytykują C++, ponieważ nigdy nie potrafili się nauczyć dobrze i prawidłowo używać C++, natomiast programiści C++ rzadko wracają do pisania w C odkąd nauczyli się dobrze i prawidłowo używać C++"

    Wnioskuję, że 90% programistów mikrokontrolerów (zwłaszcza ARM) nie zna dobrze C++ bo używa C :-)

    khoam napisał:
    labo napisał:

    Zmodyfikowałem część kodu, który zamieściłeś w poście #19 w taki sposób, aby w ogóle nie korzystać z klasy String. Detekcja i zamiana "niechcianego" znaku CR na 0 odbywa się bezpośrednio w buforze, natomiast do funkcji lcd.print() przekazywany jest wskaźnik do drugiego znaku w tym buforze (czyli z pominięciem '@'). W tej wersji kodu nie trzeba wykonywać operacji kopiowania. Powinno zadziałać :)
    Kod: c
    Zaloguj się, aby zobaczyć kod

    ZnakCR występuje w tym przypadku na końcu ciągu znaków, po co więc go szukać jak musi byc na pozycji strlen(smsbuffer)-1 ?
    Nadal uważasz,że powyższe jest prostsze niż strncpy ?
    To co powyżej może załatwić
    Kod: c
    Zaloguj się, aby zobaczyć kod

    Pomija pierwszy znak itd.
    Naprawdę nie potrafię zrozumieć, dlaczego komplikujecie sobie życie.

  • CControls
  • #32 05 Gru 2018 20:37
    khoam
    Poziom 20  

    LChucki napisał:
    ZnakCR występuje w tym przypadku na końcu ciągu znaków, po co więc go szukać jak musi byc na pozycji strlen(smsbuffer)-1 ?


    Gdybyś dobrze wczytał się w opis problemu w poprzednich postach Autora wątku, wiedziałbyś, że znak CR może i pojawia się w różnych miejscach smsbuffer. Na tym polegał generalnie problem. Wielkość smsbuffer jest stałą i nadmiarowa w stosunku do pojawiających się tam kolejno ciągu znaków generowanych przez funkcję gsm.readSMS().
    Natomiast funkcja length() zwracała wartość zero z powodu znaku CR i to też Autor wątku opisał w przeprowadzonym doświadczeniu.
    Dodatkowo po znaku CR mogły się pojawić inne znaki niż 0, a te miały być już zignorowane. - strlen() nic tu nie pomoże.
    W skrócie: gsm.readSMS() tworzyła śmietnik i trzeba było ten śmietnik uporządkować.

    Tak, jak napisałem w poprzednim poście, tworzenie przejściowych buforów łańcuchów tekstowych przez kopiowanie zawartości części smsbuffer jest zbędne w tym konkretnym miejscu kodu Autora.

  • #33 05 Gru 2018 20:52
    LChucki
    Poziom 18  

    khoam napisał:
    wiedziałbyś, że znak CR może i pojawia się w różnych miejscach smsbuffer. Na tym polegał generalnie problem.

    Może nie pojawiać się wcale albo być spacją lub innym znakiem.
    W czym problem?

  • #34 05 Gru 2018 21:16
    khoam
    Poziom 20  

    LChucki napisał:
    W czym problem?


    No chyba generalnie w tym, że kolego odpowiadasz zanim skończę pisać swoją odpowiedź do Twojego poprzedniego pytania :)

  • #35 05 Gru 2018 21:41
    LChucki
    Poziom 18  

    khoam napisał:
    LChucki napisał:
    W czym problem?


    No chyba generalnie w tym, że kolego odpowiadasz zanim skończę pisać swoją odpowiedź do Twojego poprzedniego pytania :)

    To nie pisz na raty. On-line Elektroda nie działa a ja nie będę 50 razy odświeżał postów,bo ktoś coś dopisuje i co chwila wysyła nową wersję. W ten sposób wprowadzasz bałagan do wypowiedzi.

  • CControls
  • #36 05 Gru 2018 21:43
    khoam
    Poziom 20  

    LChucki napisał:
    To nie pisz na raty. On-line Elektroda nie działa a ja nie będę 50 razy odświeżał postów,bo ktoś coś dopisuje i co chwila wysyła nową wersję. W ten sposób wprowadzasz bałagan do wypowiedzi.

    Rozumiem, że koledze skończyły się merytoryczne argumenty. Dziękuję za dyskusję.

  • #37 05 Gru 2018 22:10
    labo
    Poziom 13  

    Coś dziwnego jest z tym stringiem chyba jeszcze ... :( Albo czymś innym...
    Siedzieliśmy nad tym kilka godzin i kicha.
    Musimy ten string porozcinać na 5 innych stringów, zgodnie z podziałem średnikami.
    Napisaliśmy sobie na boku program i jak to na boku wszystko działa:

    Kod: c
    Zaloguj się, aby zobaczyć kod


    Gdy wlepiliśmy ten kod w program po otrzymanym stringu z wczoraj wcięło string nawet ze zmiennej przed tym fragmentem, który wkleiliśmy.

    Obcięliśmy kawał kodu aby "debugować" (trudne słowo) ;)
    Kod: c
    Zaloguj się, aby zobaczyć kod

    i dostajemy:
    Kod: c
    Zaloguj się, aby zobaczyć kod

    brak przypisań do zmiennej stacja


    Co ciekawsze po zmianie jednej linijki na:
    Kod: c
    Zaloguj się, aby zobaczyć kod

    co powinno wyjść na jedno mamy:
    Kod: c
    Zaloguj się, aby zobaczyć kod


    Po skasowaniu deklaracji zmiennej "znaczek" na początku programu i wpisaniu w tym miejscu:
    Kod: c
    Zaloguj się, aby zobaczyć kod


    dostajemy:
    Kod: c
    Zaloguj się, aby zobaczyć kod



    WTF??

  • #38 05 Gru 2018 22:15
    LChucki
    Poziom 18  

    Kawałek kodu obejrzałem i zastanawiam się, po co w kilkunastu stringach godzina, minuta itp? Co z tymi danymi dalej chcesz robić? Strzelam, że sscanf załatwiłby sprawę.

  • #39 05 Gru 2018 22:37
    labo
    Poziom 13  

    Poczytamy o sscanf.
    Dane przychodzą w formie SMSa: @dana1;data;czas;dana2;dana3.
    @ na początku jako odróżnienie, że to nasz SMS.
    Te pięć elementów ma byś wyświetlane w różnych miejscach na wyświetlaczu LCD,

    Kod: c
    Zaloguj się, aby zobaczyć kod
    dlatego chcieliśmy je podzielić na osobne zmienne.

    Dwie ostatnie zmienne dodatkowo po ubraniu w dodatkowe fragmenty łańcuchów, pójdą dalej w świat. String tu jest wymagany.

    EDIT: mała pomyłka.

  • #40 05 Gru 2018 22:50
    LChucki
    Poziom 18  

    labo napisał:
    Poczytamy o sscanf.
    Dane przychodzą w formie SMSa: dana1;data;czas;dana2;dana3.
    Te pięć elementów ma byś wyświetlane w różnych miejscach na wyświetlaczu LCD,
    Kod: c
    Zaloguj się, aby zobaczyć kod
    dlatego chcieliśmy je podzielić na osobne zmienne.

    Dwie ostatnie zmienne dodatkowo po ubraniu w dodatkowe fragmenty łańcuchów, pójdą dalej w świat. String tu jest wymagany.

    Trzeba było napisać o tym w pierwszym poście a nie "czarować".
    Pierwszy post nic nie mówi o SMS. Nie chce mi się na nowo odnajdować koła. Mam funkcje, które są Ci potrzebne, ale niestety w C, więc niech inni, lepsi wykażą się. Wygenerujesz kilka kB niepotrzebnego kodu ale będzie działać! Ja bym to zrobił po swojemu, strstr albo, skoro jeden znaczek, można "zaoszczędzić"
    i pętla for. W wyniku zwracasz (jak strstr) wskaźnik,gdzie znaleziono (lub nie) poszukiwany ciąg (znak) i następne szukanie. Poczekam,co inni "wyprodukują" a później dam "gorsze" (jak w przypadku nieszczęsnego CR, zera) rozwiazanie.
    Pewnie Ci, co potrafią używać C++ lepiej niż ja i tysiące innych osób C, dadzą rozwiązanie co nie pochłonie całej RAM w AVR.

  • #41 05 Gru 2018 23:03
    labo
    Poziom 13  

    LChucki napisał:

    Trzeba było napisać o tym w pierwszym poście a nie "czarować".
    Pierwszy post nic nie mówi o SMS.

    Wiesz, w swej niewiedzy nie myślałem, że to istotne. Tabela znakowa to dla mnie tabela znakowa, nie miało znaczenia skąd.

    Dziękuję, i tak wiele nam pomogłeś.

    Chłopak robi dwa urządzenia. Pierwsze jest gotowe, pobiera dane i wysyła dzielone separatorem ";" i na początku z "@" (jako odróżnienie, że to nasz) SMSem do tego drugiego w którym dane trzeba wyświetlić w odstępach na LCD. To priorytet. Jak zadziała, to dwie ostatnie by chciał jeszcze "opakować" dodatkowymi informacjami i wysłać dalej koniecznie jako String, ale to przyszłość. Najpierw trzeba wyświetlić wszystko na LCD. Niby proste, ale ciągle coś nie tak. Na boku wszystko działa, w kupie nie chce.

    EDIT: drobna poprawka

  • #42 05 Gru 2018 23:23
    LChucki
    Poziom 18  

    labo napisał:
    LChucki napisał:

    Trzeba było napisać o tym w pierwszym poście a nie "czarować".
    Pierwszy post nic nie mówi o SMS.

    Wiesz, w swej niewiedzy nie myślałem, że to istotne. Tabela znakowa to dla mnie tabela znakowa, nie miało znaczenia skąd.

    Dziękuję, i tak wiele nam pomogłeś.

    Chłopak robi dwa urządzenia. Pierwsze jest gotowe, pobiera dane i wysyła dzielone separatorem ";" i na początku z "@" SMSem do tego drugiego w którym dane trzeba wyświetlić w odstępach na LCD. To priorytet. Jak zadziała, to dwie ostatnie by chciał jeszcze "opakować" dodatkowymi informacjami i wysłać dalej koniecznie jako String, ale to przyszłość. Najpierw trzeba wyświetlić wszystko na LCD. Niby proste, ale ciągle coś nie tak. Na boku wszystko działa, w kupie nie chce.

    Jak mi teraz napiszesz, że używacie RPi, to się załamię. Tam to w jednej linijce się robi.

  • #44 06 Gru 2018 09:50
    LChucki
    Poziom 18  

    Skoro oba urządzenia robicie sami, to po co sobie utrudniacie życie jakimiś CR? Nie prościej wysłać bez niego?
    Kolejne ułatwienie stała długość ramki. Rozkodowanie jej (do zmienny,bo pewnie będą do czegoś używane) to jedna instrukcja sscanf. Przykładowe "@8;2018-12-2;22:22:34;234;33" można zrobić tak:

    Code:

    sscanf( buforsms+1, "%d;%d-%d-%d;%d..itd", &zmienna1, &zmienna2, &zmienna3, idt );

    Przesłanie dalej przez sprintf
    Code:

    sprintf( buforsms "@%d;%4d-%02d-%02d;%02d..itd", &zmienna1, &zmienna2, &zmienna3, idt );

    Jak byś napisał o co Ci chodzi w pierwszym poście, dawno już byś miał gotowe rozwiązanie, "aż" dwie linijki kodu. A tak dwie strony, ponad 40 postów, hektolitry kodu, szukanie jakiś CR, konwersje char - >String i inne cuda na kiju.

    Dodano po 6 [minuty]:

    Na LCD,z odstępami, możesz wyświetli tak
    Code:

    sprintf( buforsms "@%d;%4d-%2d-%2d;%2d..itd", &zmienna1, &zmienna2, &zmienna3, idt );
    LCD.Print( buforsms );

    Nie pamiętam, czy w GCC, nie trzeba spacji przed liczbą cyfr czyli "% 4d" zamiast "%4d".

  • #45 06 Gru 2018 10:17
    labo
    Poziom 13  

    LChucki napisał:
    Skoro oba urządzenia robicie sami, to po co sobie utrudniacie życie jakimiś CR? Nie prościej wysłać bez niego?


    Niestety my tego CR nie doklejamy. Musi to robić operator sieci GSM, bo ten CR się pojawia zarówno w SMSach wysłanych przez nasze urządzenie czy przy wysłaniu SMSa z komórki.

    LChucki napisał:
    Kolejne ułatwienie stała długość ramki.

    właśnie czytam o sscanf i widzę, że skoro u nas ostatnie dwie dane mogą mieć postać 1,2 lub 3 znakową
    @8;2018-12-2;22:22:34;xxx;xxx
    @8;2018-12-2;22:22:34;xx;xx
    @8;2018-12-2;22:22:34;x;x
    i jeszcze ich wariacje xxx;x itd., to chyba trzeba będzie dopełniać zerami 00x do trzech miejsc (więcej niż 3 nie będzie).

    A czy można odczytać tak, aby cała data i godzina była w zmiennej String? (String, bo już z kreskami.)
    Kod: c
    Zaloguj się, aby zobaczyć kod


    Sprawdzić i odezwać się będę mógł dopiero popołudniu. Jeszcze poczytać o sprintf muszę co to robi.

    Żeby takie rzeczy na starość... ;)

  • #46 06 Gru 2018 10:28
    LChucki
    Poziom 18  

    labo napisał:
    że skoro u nas ostatnie dwie dane mogą mieć postać 1,2 lub 3 znakową
    @8;2018-12-2;22:22:34;xxx;xxx
    @8;2018-12-2;22:22:34;xx;xx
    @8;2018-12-2;22:22:34;x;x
    i jeszcze ich wariacje xxx;x itd., to chyba trzeba będzie dopełniać zerami 00x do trzech miejsc (więcej niż 3 nie będzie).

    Najlepiej dopełnić zerami (formatowanie w sprintf przez %03d). Jeśli z jakiś powodów jest to niemożliwe, to z sscanf jest więcej zabawy. Sscanf zwraca wskaźnik na ciąg, który analizował. Trzeba konwersje przeprowadzać po jednej zmiennej, za każdym razem wskazując na kolejny ciąg. Można użyć strstr do szukania kolejnych danych (znaku średnika). W każdym razie jest z tym trochę zabawy. No i sscanf na AVR-GCC potrafi działać tylko na int, więc o log można zapomnieć. Na float działa ale trzeba doinstalować biblioteki, może w Arduino są już zainstalowane.

    labo napisał:
    A czy można odczytać tak, aby cała data i godzina była w zmiennej String? (String, bo już z kreskami.)

    Naturalnie. Użyj strncpy, coś tak
    Code:

    strncpy( buf, bufsms+2, 9 );

    Sscanf zrobisz z ofsetem + 10 (bufsms+10).

  • #47 06 Gru 2018 19:58
    labo
    Poziom 13  

    Ten sscanf, to jakaś ściema, albo to całe Arduino...
    Mam program na którym testuję:

    Kod: c
    Zaloguj się, aby zobaczyć kod


    Dostaję porawnie:
    Kod: c
    Zaloguj się, aby zobaczyć kod


    Teraz zmieniam tylko kolejność (!!) w deklaracji zmiennych, przenoszę
    char godzina[5]; dwie linijki wyżej:
    Kod: c
    Zaloguj się, aby zobaczyć kod


    I już dostaję zły wynik:
    Kod: c
    Zaloguj się, aby zobaczyć kod


    Toż to jest chore... :cry:

  • #48 06 Gru 2018 20:05
    LChucki
    Poziom 18  

    Dziwne zachowania = mało RAM lub "jazda" po pamięci (nadpisywanie tablic, stringów).
    Ile znaków zarezerwowałeś na stringi (npGodzina) a ile one zajmują?

  • #50 06 Gru 2018 21:01
    LChucki
    Poziom 18  

    labo napisał:
    Na razie to mały program na boku, nic jeszcze nie wklejałem w nasz program. Na razie testuję sobie zachowanie sscanf().
    char godzina[5];

    Jeszcze raz. Ile zarezerwowałeś na "godzina" (powyżej widać) a ile zajmuje string?

  • #52 06 Gru 2018 21:19
    LChucki
    Poziom 18  

    labo napisał:
    Na zmienną godzina ma być 5 znaków w formie xx:xx
    char SMSik[160] = "@8;30;12:12;88;99"; <- w tym przypadku 12:12

    A przeczytaj, jeszcze raz, moje poprzednie wypowiedzi na temat stringów - z bielizną nie pomyl :-) Przejrzyj kody gdzie było szukanie końca tekstu i napisz ile pamięci trzeba aby zapamiętać ciąg "12:12".

  • #53 06 Gru 2018 21:29
    JacekCz
    Poziom 36  

    LChucki napisał:
    Dziwne zachowania = mało RAM lub "jazda" po pamięci (nadpisywanie tablic, stringów).
    Ile znaków zarezerwowałeś na stringi (npGodzina) a ile one zajmują?


    Kolega większość buforów znakowych dał o jeden znak za mało.
    Kod: c
    Zaloguj się, aby zobaczyć kod
    A potem mamy jak to złej baletnicy ... złośliwe środowisko przeszkadza.

    W sekwencji poprawek udzielanych na oślep autor i próbujący pomagać powstaje koszmarek z dziesiątkami subtelnych błędów

    Dodano po 2 [minuty]:

    labo napisał:
    Na razie testuję sobie zachowanie sscanf().


    Celem TESTÓW jest znalezienie sytuacji, że tworzony program (fragment) działa niezgodnie ze specyfikacją. Znasz dokładnie specyfikację sscanf?
    To nie mów, że testujesz

  • #54 06 Gru 2018 21:29
    LChucki
    Poziom 18  

    JacekCz napisał:
    Kolega większość buforów znakowych dał o jeden znak za mało.

    Musi jednak wiedzieć dlaczego. We wcześniejszych postach jest informacja na ten temat.

  • #55 06 Gru 2018 22:20
    labo
    Poziom 13  

    JacekCz napisał:


    labo napisał:
    Na razie testuję sobie zachowanie sscanf().


    Celem TESTÓW jest znalezienie sytuacji, że tworzony program (fragment) działa niezgodnie ze specyfikacją. Znasz dokładnie specyfikację sscanf?
    To nie mów, że testujesz


    Proszę nauczyć się, co oznacza w języku polskim słowo "testować".

    [url=]https://sjp.pwn.pl/szukaj/testowa%C4%87.html[/url]
    testować «poddawać kogoś lub coś testowi»
    [url=]https://sjp.pwn.pl/szukaj/test.html[/url]
    test «próba, której poddaje się urządzenie, produkt, preparat itp. w celu sprawdzenia jego składu, właściwości i działania; też: to, co służy do przeprowadzenia takiej próby»

    Testowanie, czyli sprawdzanie działania.
    A mam się uczyć tylko z książki, bez wypróbowania zdobytej wiedzy w praktyce? To tak jakbyś kazał się uczyć języka programowania bez komputera. Chyba żartujesz...

    Jedno jest niepodważalne: Kolega LChucki pomógł bardzo dużo w przeciwieństwie do innych.

  • #56 06 Gru 2018 22:35
    LChucki
    Poziom 18  

    labo napisał:
    Jedno jest niepodważalne: Kolega LChucki pomógł bardzo dużo w przeciwieństwie do innych.

    Już wiesz dlaczego deklarujesz za małe bufory? Nie napiszę teraz tego, jak wspomniałem było już o tym. Jak doczytasz, to zapamiętasz do końca życia i jeden dzień dłużej.

    Na debugerze byś ładnie widział jak zamazują się zmienne czy tablice.

    Dodano po 4 [minuty]:

    labo napisał:
    Niestety my tego CR nie doklejamy. Musi to robić operator sieci GSM, bo ten CR się pojawia zarówno w SMSach wysłanych przez nasze urządzenie czy przy wysłaniu SMSa z komórki.

    Jaki to operator? Ja tego problemu nie mam.

  • #57 07 Gru 2018 11:31
    labo
    Poziom 13  

    labo napisał:
    Jedno jest niepodważalne: Kolega LChucki pomógł bardzo dużo w przeciwieństwie do innych.

    Bardzo przepraszam Kolegę khoam, bo i jemu należą się podziękowania. Jeszcze raz przepraszam.

    LChucki napisał:
    Już wiesz dlaczego deklarujesz za małe bufory? Nie napiszę teraz tego, jak wspomniałem było już o tym. Jak doczytasz, to zapamiętasz do końca życia i jeden dzień dłużej.


    Ponieważ:
    LChucki napisał:
    rezerwując bufor na stringi, zawsze trzeba go powiększyć o kod 0.


    LChucki napisał:
    labo napisał:
    Niestety my tego CR nie doklejamy. Musi to robić operator sieci GSM, bo ten CR się pojawia zarówno w SMSach wysłanych przez nasze urządzenie czy przy wysłaniu SMSa z komórki.

    Jaki to operator? Ja tego problemu nie mam.

    Wysyłka Plus, odbiór Orange. Jak wspomniałem wyżej niezależnie czy wysyłka z urządzenia czy komórki. Jeszcze jedno, może to nie operator tylko biblioteka, której używamy do odczytu z SIM800.

    Młodzież będzie u mnie dzisiaj popołudniu, napisał, że poprawił kod "nadajnika" aby uzupełniał dane o zera, żeby ramka miała stałą długość. Wpiszemy i sprawdzimy czy działa. Później dalej będziemy siedzieć nad sscanf().

    Dzięki osobom pomagającym wiem, że nauczymy się i temat ugryziemy. Jedyne czego się boje, to końca pamięci w tym malutkim Nano.

  • #58 07 Gru 2018 11:38
    LChucki
    Poziom 18  

    labo napisał:
    Jeszcze jedno, może to nie operator tylko biblioteka, której używamy do odczytu z SIM800.

    Albo wysyłająca.

  • #59 07 Gru 2018 19:48
    labo
    Poziom 13  

    Raczej nie, bo jak wysyłamy z komórki, to też jest ten CR.

    Na razie czeka nas optymalizacja kodu nadajnika, bo jak wpisaliśmy kod dopełniający zerami, to chyba nam pamięć wyszła, bo sam kod na boku działa. Musimy trochę posiedzieć nad tym i zrobić to lepiej.

  • #60 07 Gru 2018 19:56
    LChucki
    Poziom 18  

    labo napisał:
    Na razie czeka nas optymalizacja kodu nadajnika, bo jak wpisaliśmy kod dopełniający zerami, to chyba nam pamięć wyszła

    Tak jest jak wybiera się zły mikrokontroler do zadania. Co można zrobić na 2kB kodu? Jak widać niewiele. Jakieś demo, że coś działa a nie użyteczne urządzenie.
    Weź procek co ma sensowną ilość RAM zamiast teraz siedzieć tydzień czy dwa i kombinować z optymalizacją na NANO z 2kB RAM, chyba, że to masowa produkcja w milionach sztuk, wtedy warto wydać na projekt 5 razy więcej kasy aby na mikrokontrolerze zaoszczędzić dolara.