{"id":856,"date":"2011-04-03T03:15:45","date_gmt":"2011-04-03T02:15:45","guid":{"rendered":"http:\/\/netrix.org.pl\/?p=856"},"modified":"2011-04-03T17:21:53","modified_gmt":"2011-04-03T16:21:53","slug":"operacje-na-systemie-plikow-w-systemach-windows-i-linux-w-c","status":"publish","type":"post","link":"https:\/\/netrix.org.pl\/index.php\/2011\/04\/03\/operacje-na-systemie-plikow-w-systemach-windows-i-linux-w-c\/","title":{"rendered":"Operacje na systemie plik\u00f3w w systemach Windows i Linux w C++"},"content":{"rendered":"<p>Tym razem notka o tym, w jaki spos\u00f3b mo\u017cna wykonywa\u0107 r\u00f3\u017cne operacje w systemie plik\u00f3w w wymienionych w temacie systemach. Oczywi\u015bcie ka\u017cdy programista C\/C++ zna funkcje wykonuj\u0105ce podstawowe operacje na plikach, takie jak:<\/p>\n<ul>\n<li>odczyt, modyfikacja, zapis (funkcja <a href=\"http:\/\/www.cplusplus.com\/reference\/clibrary\/cstdio\/fopen\/\">fopen<\/a> i poboczne oraz klasy <a href=\"http:\/\/www.cplusplus.com\/reference\/iostream\/fstream\/\">fstream<\/a>)<\/li>\n<li>zmiana nazwy pliku lub katalogu (funkcja <a href=\"http:\/\/www.cplusplus.com\/reference\/clibrary\/cstdio\/rename\/\">rename()<\/a>)<\/li>\n<li>usuni\u0119cie pliku (funkcja <a href=\"http:\/\/www.cplusplus.com\/reference\/clibrary\/cstdio\/remove\/\">remove()<\/a>)<\/li>\n<\/ul>\n<p>\nNieco wi\u0119cej problem\u00f3w sprawiaj\u0105 pozosta\u0142e operacje, takie jak np. pobranie pe\u0142nej \u015bcie\u017cki do pliku czy przegl\u0105danie listy plik\u00f3w w katalogu, poniewa\u017c w bibliotece standardowej nie ma do tego celu odpowiednich funkcji, zatem nale\u017cy ich szuka\u0107 w API systemu. Niestety co API to r\u00f3\u017cne funkcje, ale zdarzaj\u0105 si\u0119 i takie, kt\u00f3re istniej\u0105 w obu systemach.<\/p>\n<p>Na pocz\u0105tek pobieranie pe\u0142nej \u015bcie\u017cki do bie\u017c\u0105cego katalogu, czyli funkcja <strong>getcwd<\/strong>. Jej prototyp w systemie Windows jest nast\u0119puj\u0105cy:<\/p>\n<p><pre lang=\"cpp\">\r\n#include <direct.h>\r\nchar* _getcwd(char* _DstBuf, int _SizeInBytes);\r\n<\/pre>\n<p>a w systemie Linux:<\/p>\n<pre lang=\"cpp\">\r\n#include <unistd.h>\r\nchar* getcwd(char* _DstBuf, int _SizeInBytes);\r\n<\/pre>\n<p>\nJak wida\u0107 prototyp obu funkcji jest identyczny, wi\u0119c nic nie stoi na przeszkodzie utworzenia sobie odpowiedniego aliasu nazwy za pomoc\u0105 <strong>typedef<\/strong>.<\/p>\n<p>\nTroch\u0119 lepiej jest z funkcj\u0105 <a href=\"http:\/\/publib.boulder.ibm.com\/infocenter\/zos\/v1r10\/index.jsp?topic=\/com.ibm.zos.r10.bpxbd00\/rtsta.htm\">stat()<\/a> i jej struktur\u0105 o tej samej nazwie (thx C&#8230;, typedef needed), kt\u00f3ra istnieje w obu systemach. Funkcja ta s\u0142u\u017cy do pobierania pe\u0142nych informacji o pliku, czyli np. daty modyfikacji, typu czy rozmiaru. Jej przyk\u0142adowe u\u017cycie wygl\u0105da nast\u0119puj\u0105co:\n<\/p>\n<pre lang=\"cpp\" line=\"1\">\r\n#include <sys\/stat.h>\r\ntypedef struct stat FileStatus; \/\/ thx C\r\n\r\n\/*...*\/\r\nFileStatus fileStatus;\r\nif(stat(szFullPath.c_str(), &fileStatus) < 0)\r\n{\r\n    return;\r\n}\r\n\r\nunsigned int uFileSize = fileStatus.st_size;\t\/\/ Pobranie rozmiaru pliku\r\n<\/pre>\n<p>\nNieco gorzej jest z wyci\u0105ganiem listy plik\u00f3w w katalogu, poniewa\u017c w tym przypadku oba systemy maj\u0105 do tego r\u00f3\u017cne funkcje. W przypadku systemu Windows wygl\u0105da to tak:\n<\/p>\n<pre lang=\"cpp\" line=\"1\">\r\n#include <windows.h>\r\n\/*...*\/\r\n\r\nWIN32_FIND_DATA info;\r\nHANDLE hFind = FindFirstFile(szDirPath, &info);\r\n\r\nif(INVALID_HANDLE_VALUE == hFind)\r\n{\r\n    printf(\"Error\");\r\n    return;\r\n}\r\n\r\ndo\r\n{\r\n    if((info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0)\r\n    {\r\n        printf(\"Directory: %s\\n\", info.cFileName);\r\n    }\r\n    else\r\n    {\r\n        printf(\"File: %s\\n\", info.cFileName);\r\n    }\r\n}\r\nwhile(FindNextFile(hFind, &info) != 0);\r\n\r\nFindClose(hFind);\r\n<\/pre>\n<p>A w systemie Linux tak:<\/p>\n<pre lang=\"cpp\" line=\"1\">\r\n#include <dirent.h>\r\n#include <string.h> \/\/ c-string operations\r\ntypedef struct dirent DirEntry;\r\ntypedef struct stat DirEntryStat; \/\/ thx C again\r\n\r\nDIR* pDir;\r\npDir = opendir(szDirPath);\r\nif(pDir == null)\r\n{\r\n    printf(\"Error\");\r\n    return;\r\n}\r\n\r\nDirEntry* pDirent;\r\nDirEntryStat dirEntryStat;\r\nwhile((pDirent = readdir(pDir)) != null)\r\n{\r\n    char buffer[255];\r\n    strcpy(buffer, szDirPath);\r\n    strcat(buffer, pDirent->d_name);\t\/\/ Do ponizszej funkcji potrzebna jest sciezka z biezacego katalogu\r\n\r\n    if(stat((buffer, &dirEntryStat) < 0)\r\n    {\r\n        printf(\"Error\");\r\n        continue;\t\/\/ file corrupted... NEXT!\r\n    }\r\n\r\n    if((dirEntryStat.st_mode &#038; S_IFDIR) != 0)\t\/\/ Katalog\r\n    {\r\n        printf(\"Directory: %s\\n\", pDirent->d_name);\r\n    }\r\n    else if((dirEntryStat.st_mode & S_IFREG) != 0)\t\/\/ Plik\r\n    {\r\n        printf(\"File: %s\\n\", info.pDirent->d_name);\r\n    }\r\n}\r\n\r\nclosedir(pDir);\r\n<\/pre>\n<p>\nMo\u017cna zauwa\u017cy\u0107, \u017ce funkcja z WinAPI jest nieco przyja\u017aniejsza, poniewa\u017c operuje na uchwycie do \u017c\u0105danego katalogu, w przeciwie\u0144stwie do funkcji Linuksowej, kt\u00f3ra po prostu zwraca nazw\u0119 tego co siedzi w katalogu i nic wi\u0119cej.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Tym razem notka o tym, w jaki spos\u00f3b mo\u017cna wykonywa\u0107 r\u00f3\u017cne operacje w systemie plik\u00f3w w wymienionych w temacie systemach. Oczywi\u015bcie ka\u017cdy programista C\/C++ zna funkcje wykonuj\u0105ce podstawowe operacje na plikach, takie jak: odczyt, modyfikacja, zapis (funkcja fopen i poboczne oraz klasy fstream) zmiana nazwy pliku lub katalogu (funkcja rename()) usuni\u0119cie pliku (funkcja remove()) Nieco [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[12],"tags":[179,149,150,151,181,152,153,154,116],"_links":{"self":[{"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/posts\/856"}],"collection":[{"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/comments?post=856"}],"version-history":[{"count":21,"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/posts\/856\/revisions"}],"predecessor-version":[{"id":877,"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/posts\/856\/revisions\/877"}],"wp:attachment":[{"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/media?parent=856"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/categories?post=856"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/netrix.org.pl\/index.php\/wp-json\/wp\/v2\/tags?post=856"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}