Introduction à la lecture et à l'écriture de fichiers PHP

巴扎黑
Libérer: 2023-03-15 06:36:01
original
1641 Les gens l'ont consulté

L'éditeur ci-dessous vous proposera un article banal sur l'écriture et la lecture de fichiers PHP (un article à lire absolument). L'éditeur le trouve plutôt bon, je vais donc le partager avec vous maintenant et le donner comme référence pour tout le monde. Suivons l'éditeur et jetons un coup d'œil

Aperçu de l'article :

1. Idées de base pour réaliser la lecture et l'écriture de fichiers

2. Utilisez la méthode fopen pour ouvrir le fichier

3. Opérations de lecture et d'écriture de fichiers

4. Utilisez la méthode fclose pour fermer le fichier

5. Mouvement du pointeur de fichier

6. Retour chariot et saut de ligne sous Windows et UNIX

1. L'idée de base de​​mettre en œuvre la lecture et l'écriture de fichiers :

1. Ouvrez le fichier via la méthode fopen : $fp =fopen(/*paramètre, paramètre*/), fp est le type de ressource
2. Effectuer des opérations de lecture ou d'écriture de fichier (la fonction utilisée ici prend le $fp renvoyé en 1 comme paramètre)
3. Appelez fclose($fp) pour fermer le fichier

. Deux : utilisez la méthode fopen pour ouvrir le fichier

fopen (chemin du fichier [chaîne], mode d'ouverture [chaîne])

<1> premier de fopen Le premier paramètre est le chemin du fichier
La façon d'écrire le chemin du fichier : 1 chemin absolu, 2 chemin relatif

1 chemin absolu. :

Les amis qui travaillent sous Windows devraient le connaître. Le séparateur de chemin sous Windows est "" au lieu de "/", mais nous ne pouvons pas utiliser le "" officiel comme séparateur lorsque écrire le chemin

Que se passe-t-il si nous écrivons le chemin avec le délimiteur "" ?


<?php
   $fp = fopen("C:\wamp64\www\text.txt",&#39;w&#39;);
?>
Copier après la connexion

Un message d'erreur apparaît après l'exécution, indiquant que le paramètre path n'est pas valide


Il faut donc remplacer le séparateur "" par "/" :


<?php
  $fp = fopen("C:/wamp64/www/text.txt",&#39;w&#39;);
?>
Copier après la connexion

Aucune erreur n'est signalée lors de l'exécution, indiquant que les paramètres sont valide.

[Note]La fonction fopen ne peut pas comprendre le délimiteur "" Si vous souhaitez utiliser "", vous devez utiliser l'échappement, comme l'écriture. : "C:\wamp64\www\text.txt" est également possible et la fonction peut le comprendre sans signaler d'erreur. Mais même ainsi, il n'est pas recommandé d'utiliser "", car sous OS (mac) seul "/" peut être reconnu mais pas ""

Conclusion de cette section : Il est recommandé de s'en tenir à l'utilisation de "/" comme séparateur

2. Chemin relatif :

Précédent Cette section présente comment écrire des chemins absolus, mais cela pose un autre problème : la structure des répertoires du serveur peut changer de manière significative, et alors tous les chemins absolus d'origine seront réécrits. Par exemple, sur mon ordinateur, le fichier cible. le chemin est C:/wamp64/www/text.txt. Et si je renomme le dossier www en penghuwan ? Les paramètres de chemin initialement écrits ne sont pas valides. Nous avons donc introduit la méthode d'écriture de chemin relatif :


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;w&#39;);
?>
Copier après la connexion

• $_SERVER est une super variable globale de PHP (accessible n'importe où dans le code, le type est un tableau) , Le répertoire racine par défaut du serveur peut être obtenu via $_SERVER['DOCUMENT_ROOT']

Le répertoire racine par défaut du serveur peut être modifié via php.ini (vous pouvez Baidu cela par vous-même)

• $_SERVER['DOCUMENT_ROOT '] ici équivaut à C:/wamp64/www

Conclusion de cette section : Il est recommandé d'utiliser des chemins relatifs

<2>Le deuxième paramètre de fopen est le mode ouvert

Après avoir défini le mode ouvert, nous sommes équivalents à définir les autorisations pour la lecture et l'écriture ultérieures opérations :

Les modes les plus basiques :

"r": Les fichiers peuvent uniquement être lus, mais les fichiers ne peuvent pas être écrits (les opérations d'écriture sont ignoré)
"w": Peut uniquement écrire des fichiers, mais ne peut pas lire les fichiers (les opérations de lecture sont ignorées)
"a": ajouter uniquement des fichiers, similaire à "w", la différence est que "w" supprime le contenu original, "a" ne supprime pas le contenu original Il y a du contenu, ajoutez simplement le contenu


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;w&#39;);
  fwrite($fp,&#39;在写模式下写入&#39;);
  fclose($fp);
?>
Copier après la connexion

Après avoir défini les autorisations pour l'opération d'écriture, le fichier peut être écrit normalement

Ouvrir après avoir exécuté C:/wamp64/www/text.txt :

Cette fois, nous définissons les autorisations en lecture seule et essayons pour écrire du texte : 'Écrire en mode lecture seule'


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
  fwrite($fp,&#39;在读模式下写入&#39;);
  fclose($fp);
?>
Copier après la connexion

Après avoir exécuté, ouvrez C:/wamp64/www/text.txt et constatez que le contenu de le fichier n'a pas changé, indiquant que l'opération a été bloquée car les autorisations correspondantes n'ont pas été définies

.

关于打开模式的网络资料,我想大家最可能找到的是这张表:(图来自W3C)

很全面,但我觉得这张表对新手有些不太友好,让人看后不知多云。 r是只读,w是只写(原来有的内容全删除),a是追加(不删除原有内容),这都好理解。

但r+,w+,和a+的区别和联系讲的实在太模糊了呀。 这里我就想详细地讲一下r+,w+,和a+三者的区别和联系:

首先r+,w+,和a+都是可读可写的,读取时的方式是一样的,关键在于写入方式的不同:

r+: 从文件[头部][覆盖]原有内容 ([不删除]原有内容);

a+:从文件[尾部][追加]内容 ([不删除]原有内容);

w+:[完全删除]原有内容,然后[再添加]新的内容

下面我依次演示上述的结论,首先我们没有写入的时候文本是”I am initialized value”(意为我是初始值)

采用r+模式写入文本“r+ mode”


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r+&#39;);
  fwrite($fp,&#39;r+ mode&#39;);
  fclose($fp);
?>
Copier après la connexion

运行后再打开文本,发现“I am in”被“r+ mode”覆盖了:

采用a+模式写入文本“a+ mode”

基于”I am initialized value”的初始文本我们运行以下代码:


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;a+&#39;);
  fwrite($fp,&#39;a+ mode&#39;);
  fclose($fp);
?>
Copier après la connexion

I am initialized value没有被删除和覆盖,而是在后面追加了a+ mode的这一段新文本

运行多次后:

•采用w+模式写入文本“w+ mode”

基于”I am initialized value”的初始文本我们运行以下代码:


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;w+&#39;);
  fwrite($fp,&#39;w+ mode&#39;);
  fclose($fp);
?>
Copier après la connexion

运行后,我们发现”I am initialized value”已经被删除了,然后才加上了“w+ mode”这段新文本

【注意】r+,a+,w+还有一个区别是a+,w+在文件不存在时则创建文件,r+文件不存在时报错

【吐槽】:关于r+和w+,a+的区别,我找了网络上,包括W3C和各种博客文章以及那本“PHP圣经”上的各种资料,发现都是一笔带过去的,这也是我写这篇文章的原因

三.文件读取和文件写入操作

先说说几个比较重要的函数:

file_exists():判断文件是否存在,返回布尔值

filesize():判断一个文件大小,返回文件的字节数,为整型数字

unlink():删除一个文件

写入文件

fwrite(资源文件对象[string],写入方式[string]),资源文件对象即为fopen方法返回的参数,为Resource类型,写入方式可以是w(或者w+,a+,r+)

已经有上面的例子,这里就不放demo了

读取文件

这是我们要读取的文件内容:

读取文件的方式有以下几种:

1.一次读取一个字节的数据 fgetc()

2.一次读取指定的字节数的数据 fread()

3.一次读取一行数据 fgets()/fgetcsv()

4.一次读完全部数据 fpassthru()/ file()

1. 一次读取一个字节 —— 通过fgetc()获取单个字节


<?php
   $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
   $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);//打开文件
   if(file_exists("$DOCUMENT_ROOT/text.txt")){//当文件存在时,才读取内容
     while(!feof($fp)){//判断文件指针是否到达末尾
        $c = fgetc($fp);//每执行一次fgetc(),文件指针就向后移动一位
        echo $c;//输出获取到的字节
      }
    }
   fclose($fp);//关闭文件
?>
Copier après la connexion

运行:

【注意】:无论是按文本格式输入输出还是按二进制格式输出,fgetc()每次获取的是一个字节而不是一个字符

上面的例子中我们是逐个输出,现在让我们只做一次输出,看看结果怎样:


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
  echo fgetc($fp);//只做一次输出
  close($fp);
?>
Copier après la connexion

运行结果如下,我们得到的不是汉字“我”,而是一个乱码,其实这个乱码就是一个字节


<?php
   $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
   $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
   echo fgetc($fp);//连续做三次输出
   echo fgetc($fp);
   echo fgetc($fp);
   fclose($fp);
?>
Copier après la connexion

2.一次读取多个字节 ——通过fread()方法:


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
  echo fread($fp, 3);//一次输出三个字节即一个汉字字符(UTF-8)
  fclose($fp);
?>
Copier après la connexion

运行结果:

改成:


echo fread($fp, 6);
Copier après la connexion

运行结果如下,输出了6个字节也即两个汉字字符(UTF-8)

3.一次读取一行——通过fgets()获取一行内容


<?php
    $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;]
    $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);//打开文件
    if(file_exists("$DOCUMENT_ROOT/text.txt")){//当文件存在时,才读取内容
     while(!feof($fp)){//判断文件指针是否到达末尾
       $line = fgets($fp);//返回一行文本,并将文件指针移动到下一行头部
       echo $line."<br/>";//输出获取到的一行文本
     }
    }
    fclose($fp);//关闭文件
?>
Copier après la connexion

fgets()其实还有第二个参数,这个参数规定了每一行能读取的最大字节数(注意是字节数不是字符数):

【注意】在UTF-8编码下汉字3字节,字母1字节

下面我修改上面的一行,代码,使获取的每一行最大字符数为3(也即字节数为9)


$line = fgets($fp,10);
Copier après la connexion

Demo:

【注意】:这里我fgets()里第二个参数为10,为什么是10呢?因为

1.这里的长度是按字节数算的

2.一个汉字占3个字节。fgets($fp,10)代表一次最多读取10 - 1 = 9字节

4.一次读完全部文件 ——fpassthru() or file()?

fpassthru()将读取文件并直接输出(无处理过程)


<?php
   $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
   $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
   fpassthru($fp);
   fclose($fp);
?>
Copier après la connexion

运行结果:

【注意】这里需要注意一点的是,我们并没有从fpassthru($fp)获取到返回值然后echo到页面上去,也就是说这个方法是会强制输出获取的内容的,而并不是像之前例子的方法那样返回文本,允许我们保存到变量中才将其输出

将读取到的全部内容保存到一个数组中,每个数组元素为一行的内容——fille()


<?php
  $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
  $file_array = file("$DOCUMENT_ROOT/text.txt");//取到文件数组
  foreach ($file_array as $value) {//输出数组元素
    echo $value."<br/>";
  }
?>
Copier après la connexion

【注意】:这里我们并不需要写fopen和fclose哦!也就是说file()方法已经帮我们做了这一步了

四.使用fclose方法关闭文件

fclose()将返回一个布尔值,成功关闭为true,关闭失败为false(失败的情况很少出现,可不考虑)

是否打开文件后一定要关闭?

1即使不手写fclose,在PHP脚本执行结束后,也会自动关闭文件的

2但在一个长时间执行的脚本中,如果不写关闭文件的fclose(),在文件加锁的情况下会造成操作的阻塞,所以,写fclose是个好习惯

五.文件指针的移动

我们上面调用的读取文件的函数,其实都是基于文件指针去打印的,每读取一段字节内容,文件指针就向后移动一段字节长度,直到被读取的文件最大字节长度为止


<?php
     $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
     function print_file_pointer($fp){//定义一个打印文件指针位置的函数
       echo " <br/>//此时文件指针的位置:";
       echo ftell($fp)."<br/>";
     }
     $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
     echo fgetc($fp);//通过fgetc连续输出三个字节
     echo fgetc($fp);
     echo fgetc($fp);
     print_file_pointer($fp);//打印此刻文件指针的位置
     
     echo fread($fp,6);//通过fread一次输出6字节
     print_file_pointer($fp);//打印此刻文件指针的位置
     
     echo fgets($fp); //通过fgets输出一整行
     print_file_pointer($fp);//打印此刻文件指针的位置
     
     fpassthru($fp); //一次性输出全部内容
     print_file_pointer($fp);//打印此刻文件指针的位置
     
     fseek($fp, 33);//使文件指针移动到33字节位置
     print_file_pointer($fp);//打印此刻文件指针的位置
     
     rewind($fp);//使文件指针移动到0字节位置(初始位置)
     print_file_pointer($fp);//打印此刻文件指针的位置
$fclose($fp);
?>
Copier après la connexion

Demo:

所以我们需要正确理解fgets(),fpassthru()这些函数的作用:

fgets():从当前文件指针的位置到本行结束的数据,而不是一定输出一整行

fpassthru():从当前文件指针的位置到全部内容结束的数据,而不是一定输出所有的数据

但在这里你可能会有疑问:为什么输出“湖湾”后的指针位置会是17而不是15呢?按理说输出“我叫彭湖湾”这5个汉字一共占3*5 = 15个字节,多出来的17 - 15 =2字节是什么呢?

多出来的两个字节是windows下的回车换行符\n\r

\n是换行,占一字节,\r是回车,占一字节,在六中我将会介绍

六.Windows和UNIX下的回车和换行


<?php
   $DOCUMENT_ROOT = $_SERVER[&#39;DOCUMENT_ROOT&#39;];
   $fp = fopen("$DOCUMENT_ROOT/text.txt",&#39;r&#39;);
   while(!feof($fp)){
    echo fgets($fp);
    echo ftell($fp);
   }
   fclose($fp);
?>
Copier après la connexion

我们在windows下敲下回车键的时候,相当于键入了\n\r,所以“我叫彭湖湾”的15字节+“\n\r”的2字节 = 17字节

在mac下不一样的是:敲下回车键的时候,相当于只键入了\n,所以“我叫彭湖湾”的15字节+“\n”的1字节 = 16字节

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Étiquettes associées:
source:php.cn
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal
À propos de nous Clause de non-responsabilité Sitemap
Site Web PHP chinois:Formation PHP en ligne sur le bien-être public,Aidez les apprenants PHP à grandir rapidement!