Wątek przeniesiony 2015-11-29 00:05 z C/C++ przez ŁF.

Program zamieniający znaki tabulacji na spacje w pliku.

0

Witam, chciałbym napisać program, który zamienia w pliku tekstowym .txt znaki tabulacji na spacje. Na razie udało mi się napisać następująćy program, który robi to w terminalu, dla wporwadzonego tekstu. Z"Ala ma kota" wyswietla: "Ala ma kota".
Chicałbym, aby ta zmiana odbywała się w pliku, próbowałem z funkcją fopen, ale coś nie działa, nie wiem, czy to jest w ogóle dobra droga i jak się do tego zabrać.

  1. działający w terminalu program:
#include <stdio.h>
int main(int argc, char * argv[]) {
    char c;
    while ((c = getchar()) != EOF || c != '\n') {
        if (c == '\t') c ==' ';
        putchar(c);
    }
}
  1. niedzialający program z funcja fopen:
#include <stdio.h>
int main(void)
{
FILE *stream;
    stream=fopen("test.txt", "w");
    if(stream == NULL)
    {
        printf("Blad otwarcia pliku dane.txt!\n");
        return -1;
    }
    
    int main(int argc, char * argv[]) {
    char c;
    while ((c = getchar()) != EOF || c != '\n') {
        if (c == '\t') c ==' ';
        putchar(c);
    }
    fclose(stream);
    return 0;
}
  

Zaznacza, że jestem zielony w programowaniu.

0

przeczytaj komunikat jaki dostajesz, i zastanów się dlaczego go dostajesz.

0

Nie dostaje żadnego komunikatu. program działa, jakby bez błędu. W pliku test.txt zmienia się zawartość: Znika napis Ala ma kota i zostaje pusty plik.

0

No tak, nigdzie nic przecież do pliku nie zapisujesz.

0

Czy lirozumiem, ze to nie działa w ten sposób?:
1)fopen-otwiera plik
2)edycja otwartego pliku w funkcji main
3)zakmniecie pliku po edycji i zapisanie zmian
Co w takim razie robi ten program i jak go zmodyfikować, żeby to działało?

0

Musisz to robić w C++?

0

Założyłem konto, przepraszam, że nie od pierwszego postu, ja założyłem temat.
Muszę to zrobić w C, nie w C++

1

Ten drugi nawet się nie skompiluje, może nie to wkleiłeś co trzeba.
Potrzebujesz:

  1. fopen("test.txt", "rw");
  2. ftell
  3. fseek
  4. fgets
  5. fputs
    obrabiaj wiersz po wierszu.
0

Mógłbyś obszerniej powiedzieć, co to znaczy obrabiać wiersz po wierszu, za pomocą tych funkcji? Jak ich użyć? Przeczytałem na wikibooks, co robią, ale nie jestem w stanie sobie tego przełożyć na ten przykład.

1
  1. Otwierasz plik fopen
  2. Zapamiętujesz pozycje ftell
  3. Odczytujesz kolejny wiersz do bufora fgets
  4. Jeżeli nie udało się wczytać to przejdź do pkt 9
  5. Zamieniasz dla wczytanego wiersza tabulacje na spacje
  6. Przestawiasz na zapamiętaną pozycje fseek
  7. Zapisujesz wiersz fputs
  8. Przechodzisz do pkt 2.
  9. Zamykasz plik
0

W jaki sposób można zrealizować pkt 3? Trzeba wcześniej zdefiniować jakąś tablice, którą potem umieszcza się w tej funkcji, czy jak? Rozumiem co się ma zadziać po polsku, ale nie wiem jak to zastosować na C.

0
Czarny Samiec napisał(a):

W jaki sposób można zrealizować pkt 3? Trzeba wcześniej zdefiniować jakąś tablice, którą potem umieszcza się w tej funkcji, czy jak? Rozumiem co się ma zadziać po polsku, ale nie wiem jak to zastosować na C.

Przepraszam za to zamieszanie z kontami, zmieniłem przeglądarkę i nie byłem zalogowany.

0

np:

char bufor[1024+1];
0

Na razie mam coś takiego, rozumiem, że to jest etap po pkt. 3. Proszę powiedzieć, czy to jest dobrze zrealizowane:

#include <stdio.h>
int main(void)
{
char bufor[1024+1];
FILE *stream;
	
	stream=fopen("test.txt", "rw");
	if(stream == NULL)
	{
		printf("Blad otwarcia pliku dane.txt!\n");
		return -1;
		
		fseek(f, 1, 1);
		result = fgets (bufor, 1025, FILE *stream);
	}
	
	fclose(stream);
	return 0;
}

I teraz moje pytanie, jak zrealizować pkt 5, czyli zamianę tabulacji w wierszu na spacje, i jak to przesuwać dalej wierszami, w sensie skąd program ma wiedzieć, kiedy przesunąć na kolejny wiersz? Czy to ma być jakaś pętla z rosnącą liczbą wierszy aż do końca pliku?

0

masz 1,6,3,9 (właśnie w tej kolejności) z tym że 6,3 nigdy się nie wykonają bo są po return, nie wspominając już o tym że absolutnie niepoprawnie zrealizowane, nawet się nie kompiluje twoje "coś takiego".

0
#include <stdio.h>
int main(void)
{
char bufor[1024+1];
FILE *stream;
	
	stream=fopen("test.txt", "rw");
	if(stream == NULL)
	{
		printf("Blad otwarcia pliku dane.txt!\n");
		return -1;
	}
		
    		long offset = ftell(stream);
		result = fgets (bufor, 1025, FILE *stream);
		fseek(f, 1, 1);
	fclose(stream);
	return 0;
}

Czy teraz jest dobrze poprawione? Dodałem linie, z funkcją ftell oraz wyrzuciłem poza nawias, żeby nie było po return. Ponadto nadal nie wiem, jak zrealizować takie zmienianie znaki tabulacji na spacje w wierszu.

0

nie lepiej jest sprawdzic ile potrzeba miejsca w pamieci, a potem zmallocowac sobie tyle ile potrzeba? jak skopiujesz to zapisujesz znak w do pliku, przed tym sprawdzajac czy zapisywany znak jest == '\t', jezeli tak to zamieniasz na (chyba) 4 spacje i tyle

0

Jak sprawdzić, ile potrzeba miejsca w pamięci?
Co to znaczy zmallocowac i jak to zrobić?
jak zapisać sprawdzony znak do pliku, a potem sprawdzać następny?
łopatologicznie, jak dziecku, po kolei i od podstaw. Błagam....

0

Wcale nie musi alokować żadnej pamięci. Wystarczy prosta funkcja:

#include <stdio.h>

void seekTab(const char* path){
    FILE* file = fopen(path,"r+");
    if(file){
        char character;
        while((character = fgetc(file)) != EOF){
            if(character == '\t'){
                fseek(file,-1,SEEK_CUR);
                fputc(' ', file);
                fseek(file,2,SEEK_CUR);
            }
        }
        fclose(file);
    }
    else printf("Cannot open specified file: %s\n", path);
}

int main() {
    seekTab("test.txt");
    return 0;
}
0
grzesiek51114 napisał(a):

        while((character = fgetc(file)) != EOF){
            if(character == '\t'){
                fseek(file,-1,SEEK_CUR);
                fputc(' ', file);
                fseek(file,2,SEEK_CUR);
            }
      

Po pierwsze, czy da się zrobić tak, żeby plik źródłowy został bez zmian a w nowym pliku był tekst, ze spacjami zamiast tab?(próbowałem wywołać program w ten sposób: ./nazwaprogramu C://ścieżka >wynik.txt, ale zmiana jest w pliku wejsciowym a tworzony jest pusty plik).
Po drugie, czy mógłbyś mi wyjaśnić, po zdaniu, te linie kodu, co one dokładnie robią w tym przykładzie?

0
// ponieważ `fgetc` przewija wskaźnik pozycji w pliku o `1` musisz go sobie cofnąć...
fseek(file,-1,SEEK_CUR);
// ...żeby móc zastąpić odczytany znak spacją...
fputc(' ', file);
// ...i znowu przewinąć do pozycji za podmienionym znakiem.
fseek(file,2,SEEK_CUR);

Po pierwsze, czy da się zrobić tak, żeby plik źródłowy został bez zmian

Da się. Potrzebujesz utworzyć jeszcze plik docelowy. CPP Reference Twoim przyjacielem: http://www.cplusplus.com/reference/cstdio/fopen/

0

Gdzie powinienem szukać tego na tej stronie? W opisie tej funkcji fopen tego nie widze... Za pomocą którejś z wymienionych po lewej funkcji?
@Edit: ogólnie bardzo dziękuję za wytłumaczenie. Jeszcze mam ostatnią prośbę co do tego kodu, co dokładnie oznacza SEEK_CUR w funkcji fseek?

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