【问题标题】:How do you 'release' an XMLWriter from an array?如何从数组中“释放”一个 XMLWriter?
【发布时间】:2021-09-22 00:48:40
【问题描述】:

[我已更新问题以添加问题是由使用数组引起的事实。]

来自XMLWriter::openUri PHP 文档的Notes section

在 Windows 上,使用此功能打开的文件会被锁定,直到写入器被释放。

如果我使用一个简单的变量来分配一个 XMLWriter 对象,unlink 会完成这项工作并释放文件。
但是如果使用XMLWriters的数组(我必须同时生成多个文件),仍然有一个/一些锁定的文件,只有在脚本结束后才会被删除。。 p>

如何“释放所有作者”并立即删除文件以便删除文件夹?

使用XMLWriter::openMemory 来“替换”用openURI 打开的文件是可行的,但感觉就像一个黑客......

三个循环只是为了复制我的真实代码的工作方式。

$tmp_dir = sys_get_temp_dir().'\dummy2';
mkdir($tmp_dir);
$xml = [];
foreach(['A', 'B'] as $a) {
    $xml[$a] = new XMLWriter();
}
foreach ($xml as $k => $x) {
    $x->openURI($tmp_dir.'\any'.$k.'.xml');
    $x->setIndent(true);
    $x->setIndentString('');
    $x->startDocument('1.0', 'UTF-8');
    $x->startElement('ELEM');
    $x->writeAttribute('ATTRIB', 'SOME_'.$k);
    $x->text('Witty');
    $x->endElement();
    $x->endDocument();
}
foreach ($xml as $k => $x) {
    $x->flush();
    unset($xml[$k]);      //unset alone doesn't clears the file handles
    //$xml->openMemory(); //This works, but seems hacky
}
unset($xml);  // This doesn't clear it either

array_map('unlink', glob($tmp_dir.'\*.*'));
rmdir($tmp_dir);  //Doesn't work, because there is still one, locked, XML file in the folder

// Script ends, file is gone from folder...

【问题讨论】:

  • OOP example 使用 outputMemory() 作为其最后一次调用。您是否尝试过查看是否会释放锁定的文件?
  • 使用unset,您可能还必须手动告诉GC 收集:stackoverflow.com/a/54163490/231316。至于 hacky,不幸的是 PHP 开发人员没有足够的时间在每个平台上测试/处理/解决,所以我认为这是你最好/最安全的选择
  • @KimHallberg openMemory() 仅用于(作为黑客)“关闭”openURI() 打开的句柄。 @ChrisHaas 垃圾收集似乎没有效果。我暂时保留这种hacky方式,希望从长远来看它不会对内存造成太大影响。
  • @Goozak 我没有说openMemory() 我说这个例子使用了outputMemory() 并问你是否尝试过。

标签: php arrays


【解决方案1】:

所以,最终循环中的unset( $x )unset( $xml[$k] )而不是),然后是unset( $xml ) 是解决方案。没有文件锁也不需要调用多余的openMemory()

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-12-19
    • 2020-09-23
    • 1970-01-01
    • 1970-01-01
    • 2018-10-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多