• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

[C] Funkcja łącząca pojedyncze znaki z konwersją typów.

Object Storage Arubacloud
0 głosów
575 wizyt
pytanie zadane 10 grudnia 2017 w C i C++ przez Tomek Wilnowski Użytkownik (610 p.)
#include <string.h>
#include <stdio.h>

char zlap_wiersz[80]; 
char wiersz[80];

void func_zlap_wiersz(int znak){
	
	if (znak == 13){
		wiersz = zlap_wiersz; /* zrzucenie wyniku do innej zmiennej error: c:49.10 */
		zlap_wiersz = 0; /* wyzerowanie zmiennej tak abym mógł jej znowu użyć error: c:50.15 */
	}

	if (znak != 13){
		const const char *dodaj_znak = (char)znak; /* rzutowanie liczby na typ char error: c:54.34 */
		strcat(zlap_wiersz, dodaj_znak); /* scalenie znaków */
	}
	
}

main.c:49:10: error: assignment to expression with array type
   wiersz = zlap_wiersz;
          ^
main.c:50:15: error: assignment to expression with array type
   zlap_wiersz = 0;
               ^
main.c:54:34: warning: initialization makes pointer from integer without a cast [-Wint-conversion]
   const const char *dodaj_znak = (char)znak;

Potrzebuję łapać pojedyncze znaki przychodzące z pliku i scalać je w kompletny cały wiersz, a następnie zapisać go do dynamicznej tablicy. W wejściu funkcji przychodzi mi liczba która odpowiada kodowi ASCII mojej pojedynczej litery słowa. Tą funkcję chcę wywołać w pętli w której przyjmuje po kolei wszystkie znaki z pliku, ale mam parę problemów i chciałbym prosić o pełne ich zrozumienie, a tutaj może kuleć moja znajomość wskaźników.

1. Jak zadeklarować zmienne  "zlap_wiersz" , "wiersz" tak aby były przygotowane na przyjęcie zmiennej ilości znaków?

2. Jak poprawnie dokonać rzutowania czy jest ono tutaj konieczne czy zwykle przypisanie liczby do char spowoduje jej rzutowanie na ten typ?

3. Jak poprawić moje błędy i dlaczego w ten sposób? 

2 odpowiedzi

0 głosów
odpowiedź 11 grudnia 2017 przez mokrowski Mędrzec (155,460 p.)
wybrane 20 grudnia 2017 przez Tomek Wilnowski
 
Najlepsza
#include <string.h>
#include <stdio.h>

/* Masz powód by te bufory były widoczne poza tą jednostką translacji? 
 * Jeśli nie to static..
 * Dzięki static "za darmo" masz także zerowanie tych tablic.
 */
static char zlap_wiersz[80];
static char wiersz[80];

void func_zlap_wiersz(int znak){

    /* Bo znak 13 to inaczej '\r'. Tak jest jaśniej.
     * Jesteś pewien że nie chodzi Ci o '\n' ?
     */
    if (znak == '\r'){
        strcat(wiersz, zlap_wiersz);
        zlap_wiersz[0] = '\0';
    } else {
        strncat(zlap_wiersz, (const char *)&znak, 1);
    }
}

int main(void) {
    /* Naiwny test... */

    /* Pierwsze użycie */
    func_zlap_wiersz((int)'A');
    func_zlap_wiersz((int)'n');
    func_zlap_wiersz((int)'n');
    func_zlap_wiersz((int)'a');
    func_zlap_wiersz((int)'\r');
    printf("%s\n", wiersz);
    wiersz[0] = '\0';

    /* Ponowne użycie... */
    func_zlap_wiersz((int)'Z');
    func_zlap_wiersz((int)'u');
    func_zlap_wiersz((int)'b');
    func_zlap_wiersz((int)'i');
    func_zlap_wiersz((int)'\r');
    printf("%s\n", wiersz);
    wiersz[0] = '\0';

    return 0;
}
0 głosów
odpowiedź 11 grudnia 2017 przez j23 Mędrzec (194,920 p.)

wiersz = zlap_wiersz;

strcpy()

zlap_wiersz = 0;

zlap_wiersz[0] = 0;

 const const char *dodaj_znak = (char)znak;

strcat(zlap_wiersz, dodaj_znak);

size_t n = strlen(zlap_wiersz);
zlap_wiersz[n++] = (char)znak;
zlap_wiersz[n] = 0;

 

komentarz 11 grudnia 2017 przez Tomek Wilnowski Użytkownik (610 p.)
/* Funkcja lapiaca wiesz */
void func_zlap_wiersz(int znak){
    
	size_t n = strlen(zlap_wiersz);
        zlap_wiersz[n++] = (char)znak;
        
	if (znak == 13){
		strcpy(wiersz, zlap_wiersz);
		zlap_wiersz[n] = 0;
	}
}

Wielkie dzięki za pomoc, ale jeszcze coś jest nie tak, bo piszę jeszcze jakoś systemowi po pamięci.

"Naruszenie ochrony pamięci" Drukuje mi tylko 15/10 000 wyrazów z pliku, a kompilator nie wywala żadnego błędu.

komentarz 11 grudnia 2017 przez j23 Mędrzec (194,920 p.)

Jak już modyfikujesz kod, który podałem, to postaraj się go zrozumieć:

void func_zlap_wiersz(int znak){

        if (znak == '\r'){ // IMO powinno być '\n'
                strcpy(wiersz, zlap_wiersz);
                zlap_wiersz[0] = 0;
                return;
        }
     
        size_t n = strlen(zlap_wiersz);
        zlap_wiersz[n++] = (char)znak;
        zlap_wiersz[n] = 0;     // <--- to MUSI być tutaj.    

}

 

Musisz zadbać o to, żeby n nie przekroczyło zakresu tablicy zlap_wiersz. I wyzeruj gdzieś na początku programu tablice zlap_wiersz i wiersz.

komentarz 12 grudnia 2017 przez Tomek Wilnowski Użytkownik (610 p.)
edycja 12 grudnia 2017 przez Tomek Wilnowski
Dobra dzięki kod działa i działa to dla 13, bo liczba 13 w moim pliku tekstowym jest znakiem końca lini.

Zastanawiałem się już czy malloca gdzieś nie wcisnąć, ale to co dałeś wygląda bardzo logicznie. Żeby zrozumieć ten kod co podałeś na początku musiałem trochę czytać dokumentację, ale to było na pewno bardzo dobre dla mnie, jeszcze raz wielkie dzięki.

Podobne pytania

0 głosów
1 odpowiedź 123 wizyt
0 głosów
3 odpowiedzi 452 wizyt
pytanie zadane 24 marca 2016 w C i C++ przez Shiro Stary wyjadacz (10,300 p.)
0 głosów
2 odpowiedzi 1,067 wizyt
pytanie zadane 14 kwietnia 2019 w C i C++ przez linq Początkujący (420 p.)

92,568 zapytań

141,422 odpowiedzi

319,638 komentarzy

61,957 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj.

Akademia Sekuraka

Kolejna edycja największej imprezy hakerskiej w Polsce, czyli Mega Sekurak Hacking Party odbędzie się już 20 maja 2024r. Z tej okazji mamy dla Was kod: pasjamshp - jeżeli wpiszecie go w koszyku, to wówczas otrzymacie 40% zniżki na bilet w wersji standard!

Więcej informacji na temat imprezy znajdziecie tutaj. Dziękujemy ekipie Sekuraka za taką fajną zniżkę dla wszystkich Pasjonatów!

Akademia Sekuraka

Niedawno wystartował dodruk tej świetnej, rozchwytywanej książki (około 940 stron). Mamy dla Was kod: pasja (wpiszcie go w koszyku), dzięki któremu otrzymujemy 10% zniżki - dziękujemy zaprzyjaźnionej ekipie Sekuraka za taki bonus dla Pasjonatów! Książka to pierwszy tom z serii o ITsec, który łagodnie wprowadzi w świat bezpieczeństwa IT każdą osobę - warto, polecamy!

...