linux中文件I/O操作(系統I/O)

来源:http://www.cnblogs.com/wurenzhong/archive/2017/09/10/7500867.html
-Advertisement-
Play Games

我們都知道linux下所有設備都是以文件存在的,所以當我們需要用到這些設備的時候,首先就需要打開它們,下麵我們來詳細瞭解一下文件I/O操作。 用到的文件I/O有以下幾個操作:打開文件、讀文件、寫文件、關閉文件等,對應用到的函數有:open、read、write、close、lseek(文件指針偏移) ...


我們都知道linux下所有設備都是以文件存在的,所以當我們需要用到這些設備的時候,首先就需要打開它們,下麵我們來詳細瞭解一下文件I/O操作。

用到的文件I/O有以下幾個操作:打開文件、讀文件、寫文件、關閉文件等,對應用到的函數有:open、read、write、close、lseek(文件指針偏移)

文件描述符:對於內核而言,所有打開的文件都通過文件按描述符引用。文件描述符是一個非負整數。
                      當打開一個現有文件或者創建一個新文件時,內核向進程返回一個文件描述符。
                      當讀、寫一個文件時,使用open/creat返回的文件描述符標識該文件,將其作為參數傳送給read或write。

linux系統下文件描述符0是標準輸入,1是標準輸出,2是標準出錯,所以一般打開文件的時候文件描述符都是從3開始。 這裡read和write是不能格式化讀取和寫入,如果想瞭解文件怎麼格式化讀取和寫入的話,可以看看我以前寫的一篇隨筆。

 

一、打開文件1)頭文件
       #include <sys/types.h>
       #include <sys/stat.h>
       #include <fcntl.h>2)函數原型    int open(const char *pathname, int flags);

      參數:
      a、pathname:打開或者創建的文件名字,如"text"
      
      b、 flags:
         O_RDONLY:只讀打開
         O_WRONLY:只寫打開
         O_RDWR:讀、寫打開
         O_CREAT:若此文件不存在則創建它,使用O_CREAT時後面要跟文件的訪問許可權位,如O_CREAT,0777
         O_APPEND:每次寫時都追加到文件的尾端
         O_EXCL :如果同時指定了O_CREAT,而文件已經存在,則出錯,用此可以測試一個文件是否
                  存在,如果不存在,則創建此文件,這使測試和創建兩者成為一個原子操作
         O_DSYNC:使每次write等待物理I/O操作完成,但是如果該寫操作並不影響讀取剛寫入的
                  數據,則不需等待文件屬性被更新
         O_NONBLOCK :如果path引用的是一個FIFO、一個塊特殊文件或一個字元特殊文件,則
                      此選項為文件的本次打開操作和後續的I/O操作設置非阻塞方式
         O_NOCTTY:如果path引用的是  終端設備,則將該設備分配為此進程的控制終端
         O_SYNC:使每次write要等待物理I/O操作完成,包括有該write引起的文件屬性更新所需的I/O
         O_TRUNC:如果文件存在,並且是常規文件而且以讀寫或者只寫打開,則將其長度截斷為0,
                  如果文件是FIFO或終端設備文件,O_TRUNC標誌被忽略,否則O_TRUNC不明確
         O_DIRECTORY:如果pathname引用的不是目錄,則出錯

(3)返回值:
     成功:文件描述符
     失敗:-1     
        
二、讀取文件1)頭文件  #include <unistd.h>2)函數原型   ssize_t read(int fd, void *buf, size_t count);
     參數:
     a、fd:調用open後返回的文件描述符
     b、buf:用來存放從文件中讀到的數據的緩衝區
     c、count:讀取的位元組數
     
(3)返回值:
     成功:讀到的位元組數,如果讀到文件尾端,則返回0
     失敗:-1
     
三、寫數據1)頭文件 #include <unistd.h>2)函數原型   ssize_t write(int fd, const void *buf, size_t count);
     參數:
     a、fd:調用open後返回的文件描述符
     b、buf:從來存放數據的緩衝區
     c、count:寫入數據的位元組數

(3)返回值:
     成功:返回已寫的位元組數
     失敗:-1
     
四、關閉文件1)頭文件  #include <unistd.h>2)函數原型  int close(int fd);
     參數:
     a、fd:調用open後返回的文件描述符

  
五、文件偏移1)頭文件  #include <sys/types.h>
              #include <unistd.h>2)函數原型   off_t lseek(int fd, off_t offset, int whence);
      參數:
      a、fd:調用open後返回的文件描述符
      b、offset  和參數whence有關,通常設置為0 (according  to  thedirective whence as follows)
      c、whence:
         SEEK_SET: 將文件的偏移量設置為距文件開始處offset個位元組
         SEEK_CUR:將文件的偏移量設置為其當前值加offset個位元組,offset可為正或負
         SEEK_END: 將文件的偏移量設置為文件長度加offset,offset可為正或負
         
(3)返回值:
     成功:返回新的文件偏移量
     失敗:-1

 

下麵是代碼:

#include <sys/types.h>
#include <sys/stat.h>
#include <sys/fcntl.h>
#include <stdio.h>
#include <errno.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>

#define PATHNAME "text.txt"
#define LENGTH 4096

void error(char *name) //錯誤提示
{
    perror(name);
    exit(1);
}

int main(int argc,char *argv[])
{
    
    int fd ; //存放文件描述符
    int size1; //讀操作時的返回值
    int size; //寫操作時的返回值
    int offset; //文件偏移量
        
    //打開文件
    /*O_REWR表示已讀寫許可權打開文件,O_CREAT表示如果文件不存在則創建
    *創建的新文件的許可權為0777,即是可讀可寫可執行,O_APPEND表示
    *寫入數據時從文件尾端寫入*/
    if((fd = open(PATHNAME,O_RDWR|O_CREAT|O_APPEND,0777)) == -1)       
    {
        error("open");
    }        
    
    
    char buf[LENGTH];
    bzero(buf,sizeof(buf));
    
    //從文件中讀取數據
    if((size1 = read(fd,buf,sizeof(buf))) == -1)
    {
        error("read");
    }
    
    printf("%s\n",buf);
  
  
   char buf1[LENGTH] = "小世界";
   //寫入數據到文件中
   if((size = write(fd,buf1,sizeof(buf))) == -1)
   {
       error("write");
   }

    char buf3[LENGTH] = "hello world";
    if((size = write(fd,buf3,sizeof(buf3))) == -1)
    {
        error("write");
    }
    
    //因為寫入數據到文件中的時候已經把文件指針偏移到文件尾端了,所以要重新把文件指針偏移到文件頭,方便下麵的讀操作
    if((offset = lseek(fd,0,SEEK_SET)) == -1)
    {
        error("lseek");
    }
    
    bzero(buf,sizeof(buf));
    if((size1 = read(fd,buf,sizeof(buf))) == -1)
    {
        error("read");
    }
    printf("%s\n",buf);
    
    //關閉文件
    close(fd);
    return 0;
}
View Code

 這是我在ubuntu上運行的結果,但是有個奇怪的地方就是我在Windows下打開文件的時候沒有看到後面寫進去的內容,而且出現亂碼,在ubuntu下用cat命令卻能看到文件中的全部內容,並且沒有亂碼

  • 用cat命令打開文件
  • 終端輸出
  • windowns下打開

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 在管理端一鍵部署nfs rsync 並且實時同步 實現非密碼非互動式一鍵部署 還會繼續增加新的東西 未完待續 ip:管理 61 nfs 131 rsync 141 web 108 管理端 : 齊天大聖的總的腳本 [root@m01 tools]# cat quanwang.sh#!/bin/bash ...
  • 在上一篇博客中,寫到瞭如何使用rpm命令來安裝、卸載軟體等,但是大家都知道,各個軟體包之間可能存在依賴關係,如果安裝某個軟體需要額外的依賴其他若幹的包,那麼我們就需要將其他額外的包一個一個的安裝上去,這樣的一個過程是非常耗時的,所以出現了一個前端工具,如yum,dnf,apt-get等,本次博客就c ...
  • 音頻文件 音頻文件是對聲音進行數字轉換之後存放的數據文件,瞭解音頻數據必須先知道幾個重要概念。 1. 採樣:對聲音信息錄入時,行進的最小操作單位,一般一次採樣具有左右2個聲道,每個聲道用1或2個位元組來存儲; 這樣採樣的量化位數是8位,或16位(樣本位寬),量化位數越高聲音音質越好;就像11位電話號碼 ...
  • 一、Nginx(web伺服器) 二、LVS(調度) 1、LVS集群之原理及概述(1) 2、LVS集群之工作原理和調度演算法(2) 3、LVS集群之NAT模式實例(3) 4、LVS集群DR模式實例(4) 5、LVS集群TUN模式實例(5) 6、LVS集群ipvsadm命令和調度演算法(6) 7、記一次lv ...
  • 在代碼運行期間動態增加功能的方式,稱之為“裝飾器”(Decorator)。 由於函數也是一個對象,而且函數對象可以賦值給變數,所以通過變數也能調用該函數。 函數對象有一個__name__屬性,可以拿到函數的名字 ...
  • Python的functools模塊提供了很多有用的功能,其中一個就是偏函數(Partial function)。要註意,這裡的偏函數和數學意義上的偏函數不一樣。 在介紹函數參數的時候,我們講到,通過設定參數的預設值,可以降低函數調用的難度。而偏函數也可以做到這一點。舉例如下: int()函數可以把 ...
  • 關鍵字lambda表示匿名函數,冒號前面的x表示函數參數。 匿名函數有個限制,就是只能有一個表達式,不用寫return,返回值就是該表達式的結果。 ...
  • 一:函數作為返回值 二:閉包 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...