如何使用PHP函数fopen()与UTF 16编码创建文件? [英] How can I create a file using the PHP function fopen() with UTF 16 encoding?

查看:242
本文介绍了如何使用PHP函数fopen()与UTF 16编码创建文件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用fopen()创建基于用户输入文件名的文件。在大多数情况下,输入将是西里尔文。我想要能够看到我的电脑上的文件名,但似乎他们没有正确的编码和我的操作系统(Windows 10)显示这样的东西 - ЙосиС.txt。



Windows使用UTF-16,所以我尝试将存储名称的变量的编码转换为UTF-16,但是当使用fopen,fwrite和fclose时,我收到错误。 >

这是代码:

 <?php 
if (isset($ _ POST [submit])){
$ name = $ _POST [name];
$ file = fopen($ name.txt,a);
fwrite($ file,$ string);
fclose($ file);
}?>


解决方案

这是真的,Windows和NTFS使用UTF-16文件名,因此您可以在其名称中使用Unicode字符读取和写入文件。



但是,您需要调用相应的函数才能使用Unicode: _wfopen()(C运行时)或 CreateFileW()(Windows API)。请参阅将NTFS中的文件名存储为?。 / p>

PHP的 fopen()不调用这些函数,它使用纯旧的ANSI fopen(),显然PHP没有编译与 _UNICODE 常量,将导致 fopen()转换为 _wfopen()等等(另见如何在PHP中打开其名称中包含unicode字符的文件? glob()在Windows上找不到具有多字节字符的文件名?



请参阅下面的几个可能的解决方案。



数据库



数据库解决方案:在表中写入Unicode名称,并使用表格的主键作为文件名。



音译



您还可以使用音译(如 PHP中所述) :如何创建unicode文件名),将替换目标字符集中具有相似字符的Unicode字符。请参阅 php.net/iconv

  $ filename = iconv('UTF-8','ASCII // TRANSLIT',Žluťoučkýkůň\\\
);
//Zlutoucky kun

请注意,这可能会导致冲突,因为多个不同的Unicode字符可以被译成相同的ANSI字符序列。



编码百分比



另一个建议,如如何在PHP中使用文件系统功能,使用UTF-8字符串? ,是 urlencode 文件名(请注意,您不应该直接传递用户输入到这样的文件系统,您允许用户覆盖系统文件):

  $ name = urlencode($ _ POST [name])。 。文本; 
$ file = fopen($ name,a);



使用Windows Unicode支持重新编译PHP



如果您的最终目标是使用Unicode文件名编写文件而无需更改任何代码,则必须使用 _UNICODE 常量和Microsoft编译器在Windows上编译PHP,希望它能奏效我想不是。



最可行:WFIO



或者,您可以使用如何在具有unicode字符的PHP中打开文件在其名称?使用WFIO扩展名,并通过

  file_get_contents(wfio://你好.XML); 


I am using fopen() to create files with file names based on the user's input. In most of the cases that input will be cyrillic. I want to be able to see the file names on my computer, but seemingly they aren't with the right encoding and my OS (Windows 10) displays something like this - "ЙосиС.txt".

Windows uses UTF-16, so I tried to convert the encoding of the variable where the name is stored to UTF-16, but I got errors when using fopen, fwrite and fclose.

This is the code:

<?php
if(isset($_POST["submit"])) {
$name = $_POST["name"];
$file = fopen("$name.txt", "a");
fwrite($file, $string);
fclose($file);
}?>

解决方案

It's true that Windows and NTFS use UTF-16 for filenames, so you can read and write files with Unicode characters in their name.

However, you need to call the appropriate function in order to leverage Unicode: _wfopen() (C runtime) or CreateFileW() (Windows API). See What encoding are filenames in NTFS stored as?.

PHP's fopen() does not call either of those functions, it uses the plain old ANSI fopen(), as apparently PHP is not compiled with the _UNICODE constant which will cause fopen() to be converted to _wfopen() and so on (see also How to open file in PHP that has unicode characters in its name? and glob() can't find file names with multibyte characters on Windows?).

See below for a couple of possible solutions.

Database

A database solution: write the Unicode name in a table, and use the primary key of the table as your filename.

Transliteration

You could also use transliteration (as explained in PHP: How to create unicode filenames), which will substitute the Unicode characters that aren't available in the target character set with similar characters. See php.net/iconv:

$filename = iconv('UTF-8', 'ASCII//TRANSLIT', "Žluťoučký kůň\n");
// "Zlutoucky kun"

Note that this can cause collisions, as multiple different Unicode characters could be transliterated to the same ANSI character sequences.

Percent-encoding

Another suggestion, as found in How do I use filesystem functions in PHP, using UTF-8 strings?, is to urlencode the filename (note that you shouldn't directly pass user input to the filesystem like this, you're allowing users to overwrite system files):

$name = urlencode($_POST["name"]) . ".txt";
$file = fopen($name, "a");

Recompile PHP with Windows Unicode support

If your end goal is to write files with Unicode file names without changing any code, you'll have to compile PHP yourself on Windows using the _UNICODE constant and a Microsoft compiler, and hope it'll work. I suppose not.

Most viable: WFIO

Alternatively, you can use the suggestion from How to open file in PHP that has unicode characters in its name? and use the WFIO extension, and refer to files via the wfio:// protocol.

file_get_contents("wfio://你好.xml");

这篇关于如何使用PHP函数fopen()与UTF 16编码创建文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆