The difference between fwrite and file_put_contents in PHP

Source: Internet
Author: User
Tags mongodb postgresql redis


The same point: the File_put_contents () function writes a string to a file, which is called fopen (), fwrite (), and fclose () in turn.



Different points: using File_append in the file_put_contents () function avoids deleting what is already in the file, that is, the additional functionality when the same file is written multiple times.



For example: 

Echo file_put_contents ("Test.txt", "Hello world.") testing! ", file_append);


File_put_contents writes a string to the Test.txt as an append,


Fwrtie clears the previous record, leaving only what is currently being written


$file = fopen ("Test.txt", "w");
Echo fwrite ($file, "Hello world." Testing! ");
Fclose ($file);





File_put_contents instead of fwrite advantages of a lot



The following is the File_put_contents instance code:



<?php
$filename = ' file.txt ';
$word = "Hello!\r\nwebkaka"; Double quotes will wrap in single quotation marks do not change lines
File_put_contents ($filename, $word);
?>



The same functionality uses the Fwrite instance code:



<?php
$filename = ' file.txt ';
$word = "Hello!\r\nwebkaka"; Double quotes will wrap in single quotation marks do not change lines
$fh = fopen ($filename, "w"); W writes a append write from the beginning
Echo fwrite ($fh, $word);
Fclose ($FH);
?>



From the above two examples see, in fact, File_put_contents is fopen, fwrite, fclose of the simplified method of writing, which is good for program code optimization, on the one hand, there is a reduction in the number of code, on the other hand will not appear fclose write not strict code, In debugging, maintenance of a lot of convenience.



In the example above, File_put_contents is written from scratch, what if you want to append a write?



In the file_put_contents syntax, there is a parameter file_append, which is an append-write declaration. The instance code is as follows:



<?php
echo file_put_contents (' file.txt ', "This is another something.", file_append);
?>



File_append is an append-write declaration. In addition to writing, in order to avoid other people to operate at the same time, often need to lock the file, then need to add a LOCK_EX statement, written as follows:



<?php
echo file_put_contents (' file.txt ', "This is another something.", file_append| LOCK_EX);
?>



Note that the echo output to the display in the above code is the length of the file string being written.



Problems:



Warning:fopen (file.txt) [function.fopen]: failed to open Stream:permission denied



This problem is sometimes encountered when writing to a file because the file does not have write permissions. To avoid this error, it is necessary to use the is_writable () function when writing a file to determine whether the file is writable. The instance code is as follows:



<?php
$filename = ' file.txt ';
if (is_writable ($filename)) {
Echo file_put_contents ($filename, "This is another something.", file_append);
} else {
echo "File $filename not writable";
}
?>



Fwrite simply writes the data to the handler.
File_put_contents may need to handle CONTENXT, data type is mixed, need more processing
Although look at the File_put_contents function Description: And then call fopen (), fwrite () and fclose () function.
But there must be a slight difference, especially when writing a lot of data repeatedly, File_put_contents will undoubtedly repeat the fopen,fclose. and fwrite can be fopen,fwrite only once.



Write a simple program to test, a 250M file



<!--
<?php
$len = 1024*1024*25;
$data = Str_repeat ("-", $len);



$start = Microtime (true);
$fp = fopen ("/tmp/b", "w");
Fwrite ($fp, $data, $len);
Fclose ($FP);
$end = Microtime (true);
echo "elipsed time:". ($end-$start). " \ n ";



$start = Microtime (true);
File_put_contents ("/tmp/a", $data);
$end = Microtime (true);
echo "elipsed time:". ($end-$start). " \ n ";



silver@silver-desktop:~/php$ PHP fwrite_vs_file_put_contents.php
Elipsed time:6.0958020687103
Elipsed time:9.6280250549316
silver@silver-desktop:~/php$ PHP fwrite_vs_file_put_contents.php
Elipsed time:6.247565984726
Elipsed time:9.0449070930481
...
-->




Conclusion: Many times the result class test, explained Fopen,fwrite,fclose Way is quicker than the direct file_put_contents!



So why? View Source code



I used the ubuntu12.04.
Direct sudo apt-get source php5
Decompression: silver@silver-desktop:~/php/php5-5.3.3



Lookup function Fwrite function: silver@silver-desktop:~/php/php5-5.3.3$ grep-rn "php_function (fwrite)".
./ext/standard/file.c:1233:phpapi Php_function (fwrite)
./ext/standard/file.h:43:phpapi php_function (fwrite);



Fwrite



Find the corresponding source, the function is very simple:



<!--
Php_function (fwrite)
{
Zval *arg1;
Char *arg2;
int Arg2len;
int ret;
int num_bytes;
Long arg3 = 0;
char *buffer = NULL;
Php_stream *stream;



if (Zend_parse_parameters (Zend_num_args () tsrmls_cc, "Rs|l", &arg1, &arg2, &arg2len, &arg3) = = FAILURE) {
Return_false;
}



if (Zend_num_args () = = 2) {
Num_bytes = Arg2len;
} else {
num_bytes = MAX (0, MIN ((int) arg3, arg2len));
}



if (!num_bytes) {
Return_long (0);
}



Php_stream_to_zval (STREAM, &ARG1);



if (PG (magic_quotes_runtime)) {
Buffer = Estrndup (arg2, num_bytes);
Php_stripslashes (buffer, &num_bytes tsrmls_cc);
}
ret = Php_stream_write (stream, buffer buffer:arg2, num_bytes);
if (buffer) {
Efree (buffer);
}



Return_long (ret);
}
-->



File_put_contents
This function has a lot of processing operations.




<!--
Php_function (file_put_contents)
{
Php_stream *stream;
Char *filename;
int Filename_len;
Zval *data;
int numbytes = 0;
Long flags = 0;
Zval *zcontext = NULL;
Php_stream_context *context = NULL;
Php_stream *srcstream = NULL;
Char mode[3] = "WB";



if (Zend_parse_parameters (Zend_num_args () tsrmls_cc, "sz/|lr!", &filename, &filename_len, &data, & Flags, &zcontext) = = failure) {
Return
}
if (z_type_p (data) = Is_resource) {
Php_stream_from_zval (SRCStream, &data);
}



Context = Php_stream_context_from_zval (Zcontext, Flags & Php_file_no_default_context);



if (Flags & php_file_append) {
Mode[0] = ' a ';
else if (Flags & LOCK_EX) {
/* Check to make sure we are dealing with a regular file * * *
if (php_memnstr (filename, "://", sizeof ("://") –1, filename + filename_len)) {
if (strncasecmp (filename, "file://", sizeof ("file://") –1) {
Php_error_docref (NULL tsrmls_cc, e_warning, "Exclusive locks May is set for regular files");
Return_false;
}
}
Mode[0] = ' C ';
}
MODE[2] = ' \0′;



stream = PHP_STREAM_OPEN_WRAPPER_EX (filename, mode, (Flags & Php_file_use_include_path)? use_path:0) | Enforce_safe_mode | Report_errors, NULL, context);
if (stream = = NULL) {
Return_false;
}
if (Flags & LOCK_EX && (!php_stream_supports_lock (stream) | | Php_stream_lock (stream, lock_ex)) {
Php_stream_close (stream);
Php_error_docref (NULL tsrmls_cc, e_warning, "Exclusive locks are not supported to this stream");
Return_false;
}



if (mode[0] = = ' C ') {
Php_stream_truncate_set_size (stream, 0);
}



Switch (z_type_p (data)) {
Case Is_resource: {
size_t Len;
if (PHP_STREAM_COPY_TO_STREAM_EX (SRCStream, Stream, Php_stream_copy_all, &len)!= SUCCESS) {
NumBytes =-1;
} else {
NumBytes = Len;
}
Break
}
Case Is_null:
Case Is_long:
Case Is_double:
Case Is_bool:
Case Is_constant:
CONVERT_TO_STRING_EX (&data);



Case is_string:
if (z_strlen_p (data)) {
NumBytes = Php_stream_write (Stream, z_strval_p (data), z_strlen_p (data));
if (numbytes!= z_strlen_p (data)) {
Php_error_docref (NULL tsrmls_cc, e_warning, "only%d of%d bytes written, possibly out of free disk spaces", numbytes, Z_st Rlen_p (data));
NumBytes =-1;
}
}
Break



Case Is_array:
if (Zend_hash_num_elements (z_arrval_p (data)) {
int Bytes_written;
Zval **tmp;
Hashposition POS;



ZEND_HASH_INTERNAL_POINTER_RESET_EX (z_arrval_p (data), &pos);
while (ZEND_HASH_GET_CURRENT_DATA_EX (z_arrval_p) (data), (void * *) &tmp, &pos) = = SUCCESS) {
if (Z_TYPE_PP (TMP)!= is_string) {
Separate_zval (TMP);
Convert_to_string (*TMP);
}
if (Z_STRLEN_PP (TMP)) {
NumBytes + = Z_STRLEN_PP (TMP);
Bytes_written = Php_stream_write (Stream, Z_STRVAL_PP (TMP), Z_STRLEN_PP (TMP));
if (Bytes_written < 0 | | | bytes_written!= Z_STRLEN_PP (tmp)) {
if (Bytes_written < 0) {
Php_error_docref (NULL tsrmls_cc, e_warning, "Failed to write%d bytes to%s", Z_STRLEN_PP (TMP), filename);



} else {
Php_error_docref (NULL tsrmls_cc, e_warning, "only%d of%d bytes written, possibly out of free disk spaces", Bytes_written, Z_STRLEN_PP (TMP));
}
NumBytes =-1;
Break
}
}
ZEND_HASH_MOVE_FORWARD_EX (z_arrval_p (data), &pos);
}
}
Break



Case Is_object:
if (z_obj_ht_p (data)!= NULL) {
Zval out;
To see how the image is saved:
if (zend_std_cast_object_tostring (data, &out, is_string tsrmls_cc) = = SUCCESS) {
NumBytes = Php_stream_write (Stream, Z_strval (out), Z_strlen (out));
if (numbytes!= Z_strlen (out)) {
Php_error_docref (NULL tsrmls_cc, e_warning, "only%d of%d bytes written, possibly out of free disk spaces", numbytes, Z_st Rlen (out));
NumBytes =-1;
}
Zval_dtor (&out);
Break
}
}
Default
NumBytes =-1;
Break
}
Php_stream_close (stream);



if (NumBytes < 0) {
Return_false;
}



Return_long (numbytes);
}
-->




When do you use fwrite,file_put_contents?



1, function prototypes have explained that they handle different types of data
2, simple document processing, the pursuit of speed with fwrite
3, writing simple with file_put_contents– (what type of data can be processed, magic ah. But to understand the type-judgment mechanism, the saved data may not be what you want it to be.


Alibaba Cloud Hot Products

Elastic Compute Service (ECS) Dedicated Host (DDH) ApsaraDB RDS for MySQL (RDS) ApsaraDB for PolarDB(PolarDB) AnalyticDB for PostgreSQL (ADB for PG)
AnalyticDB for MySQL(ADB for MySQL) Data Transmission Service (DTS) Server Load Balancer (SLB) Global Accelerator (GA) Cloud Enterprise Network (CEN)
Object Storage Service (OSS) Content Delivery Network (CDN) Short Message Service (SMS) Container Service for Kubernetes (ACK) Data Lake Analytics (DLA)

ApsaraDB for Redis (Redis)

ApsaraDB for MongoDB (MongoDB) NAT Gateway VPN Gateway Cloud Firewall
Anti-DDoS Web Application Firewall (WAF) Log Service DataWorks MaxCompute
Elastic MapReduce (EMR) Elasticsearch

Alibaba Cloud Free Trail

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.