Как закрыть поток c
Перейти к содержимому

Как закрыть поток c

  • автор:

Ввод-вывод и работа с файлами

Файл в языке Си рассматривается как неструктурированная последовательность байтов. С этой точки зрения в языке программирования C файлом может быть как собственно файл на жестком диске, так и принтер, дисплей и другие подключаемые устройства ввода-вывода.

Как правило, взаимодействие между приложением и файлами производится посредством обмена блоков байт фиксированной длины (обычно длина представляет степень двойки — 256 или 512 байт).

При чтении из файла данные помещаются в буфер операционной системы, а затем побайтно передаются приложению.

При записи в файл данные накапливаются в буфере, а при заполнении буфера записываются на диск в виде единого блока байт.

Буферы представляют участки памяти, поэтому передача данных между приложением и буфером происходит довольно быстро в отличие от взаимодействия с физическими устройствами типа принтера.

Файл вместе с предоставляемыми средствами буферизации представляет поток .

Язык программирования Си содержит необходимый функционал для работы с файлами и устройствами ввода-вывода. Для применения его применения в программе необходимо подключить заголовочный файл stdio.h .

Открытие и закрытие потоков

Чтобы работать с потоком, его необходимо открыть. Для открытия потока применяется функция fopen() , которая имеет следующий прототип:

FILE * fopen(имя_файла, режим_открытия);

Первый параметр представляет имя открываемого файла, а второй задает режим открытия, от которого зависит, как файл может быть обработан.

Функция возвращает указатель на структуру, которая имеет тип FILE , определенный в том же файле stdio.h. Этот указатель идентифицирует поток в программе и через него мы сможем обращаться к открытому файлу.

При открытии поток связывается со структурой

Режимы открытия

Каждый режим задается в виде набора символов. В частности, мы можем использовать следующие режимы:

  • «w» : текстовый файл открывается для записи. Если файл ранее существовал, то он пересоздается и записывается заново
  • «r» : текстовый файл открывается для чтения
  • «a» : текстовый файл открывается для добавления в него новых данных. Если файл существовал ранее, то данные просто добавляются
  • «w+» : текстовый файл создается для записи/записи. Если файл ранее существовал, то при первой записи после открытия он пересоздается и записывается заново. А при последующих записях после открытия данные добавляются в него без перезаписи.
  • «r+» : текстовый файл открывается для чтения/записи. Запись допустима в любом месте файла, кроме конца файла, то есть недопустимо увеличение размеров файла.
  • «a+» : текстовый файл открывается или создается (при его отсутствии) для чтения/записи. В отличие от режима w+ файл при открытии не пересоздается заново, а в отличии от режима r+ можно записывать данные в конец файла
  • «wb» : бинарный файл открывается для записи
  • «rb» : бинарный файл открывается для чтения
  • «ab» : бинарный файл открывается для дозаписи
  • «w+b» : бинарный файл создается для записи/чтения
  • «r+b» : бинарный файл открывается для чтения/записи
  • «a+b» : бинарный файл открывается или создается (при его отсутствии) для чтения/дозаписи

Режимы позволяют разграничить доступ к файлу и открыть его только для чтения или только для записи или совместить оба варианта. Кроме того, на уровне режимов происходит разделение файлов на текстовые и бинарные. И программа будет обрабатывать файлы определенным образом, в зависимости какой режим будет выбран — для текстовых или бинарных файлов. Неправильно заданный режим может привести к некорректной интерпретации файла.

Закрытие файла

После завершения работы с файлом его следует закрыть. Для этого применяется функция fclose() :

int fclose(указатель_на_поток);

Единственный параметр функции представляет ранее полученный при открытии файла указатель на структуру FILE, связанный с файлом.

Функция возвращает число: 0 — в случае успешного выполнения и встроенное значение EOF в случае ошибки.

Например, откроем и закроем файл «data.txt», который расположен в одной и той же папке, что и выполняемая программа:

#include int main(void)

Если файл расположен в каком-то другом месте, то можно указать соответствующий относительный или абсолютный путь. Например, «С:\\data.txt» (если файл data.txt расположен в корне диска C).

Обработка ошибок

В процессе открытия или создания файла мы можем столкнуться с рядом ошибок, например, при открытии в режиме чтения не окажется подобного файла, недостаточно памяти и т.д. И в случае возникновения ошибки функция fopen() возвращает значение NULL . Мы можем обработать возникновение ошибки с помощью проверки результата функции:

#include int main(void) < FILE * fp= fopen("data28.txt", "r"); if(fp==NULL) < perror("Error occured while opening data28.txt"); return 1; >fclose(fp); return 0; >

Для вывода ошибки на консоль применяется встроенная функция perror() . И так как дальнейшие действия в программе в случае ошибки при открытии файла смысла не имеют, то с помощью вызова return 1; завершаем работу приложения и возвращаем число, отличное от нуля (обычно ненулевое число рассматривается как код ошибки).

И если при попытке открытия файла по указанному пути его не окажется, то консоль выведет следующую ошибку:

Error occured while opening data28.txt: No such file or directory

Как «выключить» поток?

По моей задумке, я создаю вектор потоков, запускаю его на нажатие CheckBox-а, на отжатие CheckBox-а происходит завершение потока. На деле при нажатии CheckBox-а он запускает отдельный поток, НО при отжатии CheckBox-а не отрабатывается завершение потока. Что я делаю не так ?? Вот кусок кода где происходит данное действо:

void MainWindow::start_sending(bool Value) < NewsThread *two_cl = new NewsThread(); // инициализируем второй класс if (test_checkbox_old == 0) < test_checkbox_old = test_checkbox.length(); qDebug() if (test_checkbox_old != test_checkbox.length()) < qDebug() for(int i =0; i< test_checkbox.length();i++) < if (Value == true) < if(test_checkbox[i]->isChecked() == true) < if(togled_checked_sensor[i] == 0) < qDebug() moveToThread(vector_thread[i]); vector_thread[i]->start(); > > > // обратный метод очистки if(Value == false) < if(test_checkbox[i]->isChecked() == false) < if(togled_checked_sensor[i] == 1) < togled_checked_sensor[i] = 0; qDebug() quit(); // чёт не работает vector_thread[i]->exit(); // чет тоже не работает > > > > void MainWindow::seting_clear(int i) < for (int f =0 ; f> void MainWindow::seting_clear(int i, int f) < f = f-i; for(int a =0; a> 

а вот где «работает» циклом поток

 void NewsThread::run_NEW(int i, QString str, int f) < // -- вот тут механизм гетеров сетеров Foo *FO = new Foo(); FO->setData(155); for(;;)< // вечный цикл if( QThread::currentThread()->isInterruptionRequested() ) < for (int i=0; igetData() ; usleep(100); > > > > 

Как закрыть поток c

Для работы с файлами в стандартной библиотеке определен заголовочный файл fstream , который определяет базовые типы для чтения и записи файлов. В частности, это:

  • ifstream : для чтения с файла
  • ofstream : для записи в файл
  • fstream : совмещает запись и чтение

Для работы с данными типа wchar_t для этих потоков определены двойники:

  • wifstream
  • wofstream
  • wfstream

Открытие файла

При операциях с файлом вначале необходимо открыть файл с помощью функции open() . Данная функция имеет две версии:

  • open(путь)
  • open(путь, режим)

Для открытия файла в функцию необходимо передать путь к файлу в виде строки. И также можно указать режим открытия. Список доступных режимов открытия файла:

  • ios::in : файл открывается для ввода (чтения). Может быть установлен только для объекта ifstream или fstream
  • ios::out : файл открывается для вывода (записи). При этом старые данные удаляются. Может быть установлен только для объекта ofstream или fstream
  • ios::app : файл открывается для дозаписи. Старые данные не удаляются.
  • ios::ate : после открытия файла перемещает указатель в конец файла
  • ios::trunc : файл усекается при открытии. Может быть установлен, если также установлен режим out
  • ios::binary : файл открывается в бинарном режиме

Если при открытии режим не указан, то по умолчанию для объектов ofstream применяется режим ios::out , а для объектов ifstream — режим ios::in . Для объектов fstream совмещаются режимы ios::out и ios::in .

std::ofstream out; // поток для записи out.open("hello1.txt"); // окрываем файл для записи std::ofstream out2; out2.open("hello2.txt", std::ios::app); // окрываем файл для дозаписи std::ofstream out3; out2.open("hello3.txt", std::ios::out | std::ios::trunc); // установка нескольких режимов std::ifstream in; // поток для чтения in.open("hello4.txt"); // окрываем файл для чтения std::fstream fs; // поток для чтения-записи fs.open("hello5.txt"); // окрываем файл для чтения-записи

Однако в принципе необязательно использовать функцию open для открытия файла. В качестве альтернативы можно также использовать конструктор объектов-потоков и передавать в них путь к файлу и режим открытия:

fstream(путь) fstream(путь, режим)

При вызове конструктора, в который передан путь к файлу, данный файл будет автоматически открываться:

std::ofstream out("hello.txt"); std::ifstream in("hello.txt"); std::fstream fs("hello.txt", std::ios::app);

В данном случае предполагается, что файл «hello.txt» располагается в той же папке, где и файл программы.

Вообще использование конструкторов для открытия потока является более предпочтительным, так как определение переменной, представляющей файловой поток, уже преполагает, что этот поток будет открыт для чтения или записи. А использование конструктора избавит от ситуации, когда мы забудем открыть поток, но при этом начнем его использовать.

В процессе работы мы можем проверить, окрыт ли файл с помощью функции is_open() . Если файл открыт, то она возвращает true:

std::ifstream in; // поток для чтения in.open(«hello.txt»); // окрываем файл для чтения // если файл открыт if (in.is_open())

Закрытие файла

После завершения работы с файлом его следует закрыть с помощью функции close() . Также стоит отметить, то при выходе объекта потока из области видимости, он удаляется, и у него автоматически вызывается функция close.

#include #include int main() < std::ofstream out; // поток для записи out.open("hello.txt"); // окрываем файл для записи out.close(); // закрываем файл std::ifstream in; // поток для чтения in.open("hello.txt"); // окрываем файл для чтения in.close(); // закрываем файл std::fstream fs; // поток для чтения-записи fs.open("hello.txt"); // окрываем файл для чтения-записи fs.close(); // закрываем файл >

Как закрыть поток после вызова detach()?

Author24 — интернет-сервис помощи студентам

С join всё понятно, программа ждёт, когда завершится этот поток.
Допустим я вызвал метод detach, как мне поток закрыть ?

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
void My() { // actions } void main() { thread *t = new thread(My) t->detach(); // close ? delete t; t = 0; }

94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
Ответы с готовыми решениями:

Как отделить поток с помощью detach?
Вообщем, не могу понять в чем проблема, хочу подвесить фоновый поток для отлавливания нажатий.

Необходимо закрыть поток (как?)
Создаю файл, после желаю записать в него инфу. Мне пишет, что файл уже открыт, что собственно.

Как закрыть поток OpenFileDialog?
Вот мой код using (OpenFileDialog dialog = new OpenFileDialog())// создание нового.

2443 / 1841 / 406
Регистрация: 15.12.2013
Сообщений: 8,238

ЦитатаСообщение от BeginerMan Посмотреть сообщение

Допустим я вызвал метод detach, как мне поток закрыть ?
Все, после вызова detach вы от него отказались и он пошел в свободное плавание.
7797 / 6563 / 2985
Регистрация: 14.04.2014
Сообщений: 28,700
Можно же флаг какой-то использовать, и чтобы поток его проверял.
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
Помогаю со студенческими работами здесь

Как правильно закрыть поток
Доброго времени суток. Не могу закрыть поток в методе. private static int intScaner() < .

Как закрыть поток (Thread) чтения SerialPort
Как грамотно организовать (а главное завершать) поток чтения SerialPort? Проблемы с этим кодом: .

Подскажите пожалуйста как закрыть поток не закрывая при этом socket
У меня Клиент отправляет серверу файл через socket, но потом мне нужно, чтобы сервер ответил.

Как закрыть поток в чужом процессе зная адрес этого потока
Здравствуйте, я хочу закрыть поток в чужом процессе зная адрес потока (test.dll!test001+0x60520).

Или воспользуйтесь поиском по форуму:

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *