Nowe posty

xx Dystrybucja pod HP Omen (6)
2024-03-27, 23:30:08
xx [Poradnik] Wyszukiwanie Sterowników (2)
2024-03-27, 21:08:23
lamp Problem z Linux Lite po instalacji (0)
2024-03-27, 19:50:30
xx Ile pingwinów? (1)
2024-03-27, 08:59:24
xx konfiguracja pale moon (0)
2024-03-24, 21:53:42
xx Plasma 6 w Neonie ssie trochę mniej ... (10)
2024-03-23, 02:38:11
xx problem z instalacja sterowników do karty sieciowej (3)
2024-03-18, 18:10:16
xx Plik abc.001 (1)
2024-03-17, 17:48:27
xx Zlecę dopracowanie programu w MatLab (0)
2024-03-13, 15:28:40
xx Linux Mint 21.3 XFCE brak dźwieku po paru minutach (karta muzyczna zintegrowana) (5)
2024-03-12, 23:07:01

Autor Wątek: z wykorzystaniem klas nie można sprawdzić czy plik istnieje  (Przeczytany 1324 razy)

KelThuzad

  • Gość
Mam pewien problem po tym jak staram się rozbić klasę na 2 pliki. A mianowicie w pliku my_file.cpp nie mogę użyć funkcji funkcji good(). Nie mam żadnej podpowiedzi do szybkiego wpisania good() po tym jak wpisze 3 pierwsze litery.
plik main.cpp:
#include <my_file.h>
#include <iostream>
#include <fstream>

int main()
{
    my_file file( "dane.txt" );
    if( file.if_file_is_opened() )
    {
        std::cerr << "Plik nie istnieje" << std::endl;
        return 1;
    }
    return 0;
}
plik my_file.h:
#ifndef MY_FILE
#define MY_FILE
#include <iostream>
#include <fstream>
class my_file
{
private:
    std::fstream file;
public:
    my_file ( std::string name_file );
    bool if_file_is_opened ( std::fstream file );
    bool if_file_is_empty ( /*std::fstream file*/ );
};
#endif // MY_FILE
plik my_file.cpp:
#include <my_file.h>
#include <iostream>
#include <fstream>

my_file::my_file(std::string name_file)
{
    file.open( name_file , std::ios::in );
}
bool my_file::if_file_is_opened(std::fstream file)
{
    if (/*!file.good()*/)
    {
        return true;
    }
}
bool my_file::if_file_is_empty(/* std::fstream file*/)
{
    file.seekp( 0 , std::ios::end );
    size_t size = file.tellg();
    if ( size == 0 )
    {
        std::cout << "Plik jest pusty" << std::endl;
    }
    file.seekp(0 , std::ios::beg);
}
Tam gdzie mam /*!file.good()*/ chciałem wstawić ale nie mogę? Nie mam bladego pojęcia o co chodzi przecież mam bibliotekę #include <fstream>.

Offline Paweł Kraszewski

  • Administrator
  • Guru
  • *****
  • Wiadomości: 3049
  • Lenistwo jest matką potrzeby = babcią wynalazku
    • Zobacz profil
Odp: z wykorzystaniem klas nie można sprawdzić czy plik istnieje
« Odpowiedź #1 dnia: 2016-08-21, 13:46:02 »
1. To robi 2 różne rzeczy:
#include "plik.h"
#include <plik.h>
Wersja z "" szuka pierw w katalogu lokalnym, potem w katalogach systemowych a z <> tylko w katalogach systemowych.

2. W my_file::if_file_is_opened masz dostęp do składowej file przez samo to, że jest to metoda klasy my_file. Nie musisz nic przekazywać jako argument. Dodatkowo, u mnie w obu przypadkach dopełnienie .good() działa (QtCreator 4.0.3)

3. W my_file::if_file_is_opened nie obsługujesz ścieżki nieistnienia pliku. Jak plik nie istnieje, powinieneś zwrócić false. Mam też wrażenie, że funkcja powinna zwracać true, jeżeli good() jest true, nie odwrotnie. Tak sugeruje nazwa Twojej metody.

4. W my_file::if_file_is_empty znowu zmieniasz stan pliku i go nie przywracasz (tj, na siłę zakładasz, że plik powinien być na początku - a tak naprawdę nie musi)

5. Dla lepszego zrozumienia działania swoich metod, nazwij nie nie if_... a is_... . To bardziej odzwierciedla to, co robią metody. Czyli nie if_file_is_opened a is_file_opened.

6. Pomijając if_file_is_empty, widzę dużą poprawę :)

Paweł Kraszewski
~Arch/Void/Gentoo/FreeBSD/OpenBSD/Specjalizowane customy

KelThuzad

  • Gość
Odp: z wykorzystaniem klas nie można sprawdzić czy plik istnieje
« Odpowiedź #2 dnia: 2016-08-21, 13:57:28 »
To wszystko dzięki twojemu kodu(z poprzedniego mojego postu) i aby trochę pokombinować rozdzieliłem sprawdzanie czy istnieje i czy jest pusty. U ciebie Paweł było to wszystko w jednej fajnej metodzie. Ale by mieć coś do nauki robię że niektóre metody (bo jak wyczytałem w książce i u ciebie w tym co mi pisałeś o klasach to bool if_file_is_opened ( std::fstream file ); to są metody?). Teraz niebawem przy następnych klasach chce dodać wyjątki ale jak poczytałem o tym to trochę ciężkie mi się to wydaje ale będę i tak to wprowadzał do kodu :D.
A tak jeszcze zapytam bo w punkcje 6 napisałeś że oprócz if_file_is_empty jest nawet nawet. A możesz mi wyjaśnić czy chodzi ci o nazwę (ze też tak jak zaproponowałeś z is_file_opened to tu powinno być is_file_empty) czy chodzi ci Pawle o coś innego?
« Ostatnia zmiana: 2016-08-21, 14:12:58 wysłana przez MateuszA »

Offline Paweł Kraszewski

  • Administrator
  • Guru
  • *****
  • Wiadomości: 3049
  • Lenistwo jest matką potrzeby = babcią wynalazku
    • Zobacz profil
Odp: z wykorzystaniem klas nie można sprawdzić czy plik istnieje
« Odpowiedź #3 dnia: 2016-08-21, 18:12:55 »
"Metody" to są funkcje zdefiniowane w klasach. W klasie - metoda, poza klasą - funkcja:

Tu pojawia się rozgraniczenie klasa - obiekt. W programowaniu obiektowym "klasa" to jakby przepis z książki kucharskiej - nie ma "jadalnej" formy, to tylko formułka. Na podstawie klasy (przepisu) konstruuje się obiekt (ciastko) - obiekt czasem nazywa się instancją klasy ("fizyczną realizacją przepisu").

Twoje DNA to Twoja klasa. Ty to instancja tej klasy. Jak masz brata bliźniaka jednojajowego, to jesteście dwoma instancjami tej samej klasy. Teraz mega uproszczenie: Wasze DNA definiuje metodę "powiedz(std::string co)". DNA nie potrafi mówić (nie ma strun głosowych). Nie możesz zrobić DNA_Mateusza::powiedz("Dzień dobry").  Mówić potrafią tylko instancje skonstruowane na podstawie tego DNA. Dlatego polecenie powiedz możesz skierować tylko do konkretnej instancji, np Mateusz.powiedz("Dzień dobry").

* main() jest funkcją - jest zdefiniowana poza jakąkolwiek klasą.
* plik.good() jest metodą klasy fstream (*) wywołaną na rzecz obiektu plik. plik jest jednym (z prawdopodobnie wielu) obiektów skonstruowanych według przepisu na klasę fstream.

(*) fstream jest tylko przykładem. Może istnieć dowolnie wiele różnych klas mających metodę bool good(). To, o którą klasę w rzeczywistości chodzi wynika z definicji zmiennej plik gdzieś wcześniej.

W zapisie
std::string testowy("Test me!")
x = testowy.size()
- std::string jest klasą
- testowy jest obiektem skonstruowanym na podstawie tej klasy.
- size() jest metodą klasy std::string wywoływaną na rzecz ("w kontekście") obiektu testowy.

A co do nazw - if czyta się w kontekście programistycznym zawsze jako jeżeli. Więc funkcja if_file_is_opened czyta się jako "jeżeli plik jest otwarty". No i jeżeli jest otwarty to co? To nie wynika z nazwy funkcji. Natomiast jeżeli metoda nazywa się is_file_opened to tłumaczymy to na "Czy plik jest otwarty", na co jest oczywista odpowiedź tak/nie i dokładnie wiadomo kiedy która zostanie udzielona. W kontekście metod klasy, czasami opuszcza się podmiot, jeżeli jest on właśnie tą klasą: na przykład jeżeli klasa to file to metoda nazywa się już tylko "is_opened" - "jest otwarty", bo wiadomo że chodzi o plik, jeżeli to jest metoda klasy plik...

if(file.if_file_is_opened()  == false) error();
jeżeli((jeżeli plik plik jest otwarty) równe jest nie) błąd().

if(! file.is_opened()) error();
jeżeli((plik jest otwarty) równa się nie) błąd().
Kompilatorowi jest ryba, jak nazwiesz funkcje. Ale osobie czytającej kod (także Tobie, za miesiąc - wiem co piszę) może utrudnić to życie, za zasadzie "co autor miał na myśli".
« Ostatnia zmiana: 2016-08-21, 18:19:02 wysłana przez Paweł Kraszewski »
Paweł Kraszewski
~Arch/Void/Gentoo/FreeBSD/OpenBSD/Specjalizowane customy