在解析文件之前如何跳过文件的BOM?

时间:2018-05-08 19:00:49

标签: d byte-order-mark

Unicode文件可以在文件的开头包含BOMstd.file.readText()将验证此BOM是否适合其保存的编码(字符串,wstring,dstring),但将BOM作为范围的一部分。

解析器通常不希望解析文件,而只是一个没有BOM规范的字符串,因为该类型已经知道。

我如何阅读文件并删除BOM(如果存在)?

1 个答案:

答案 0 :(得分:1)

我发现最简单的方法是利用std.encoding获取BOM并跳过它。

import std.file;
auto fileContent = readText(file);

正如Jonathan所说,它不适用于非UTF8编码,所以这里有一个经过测试的函数,可以使用string,wstring,dstring并进行测试。

import std.traits: isSomeString;

STR skipBom(STR)(STR fileContent) if(isSomeString!STR) {
    import std.encoding : getBOM, BOM;
    import std.algorithm : skipOver;
    import std.traits: CopyTypeQualifiers;
    auto byteArray = cast(CopyTypeQualifiers!(STR, ubyte[]))fileContent;
    if(getBOM(byteArray).schema != BOM.none)
        byteArray.skipOver(getBOM(byteArray).sequence);
    return cast(STR)byteArray;
} unittest {
    string s = "\xEF\xBB\xBFTesting UTF8";
    assert(skipBom(s) == "Testing UTF8");
} unittest {
    wstring s = [0xFEFF,'T', 'e', 's', 't', 'i', 'n', 'g', ' ', 'U', 'T', 'F', '1', '6'];
    assert(skipBom(s) == "Testing UTF16");
} unittest {
    dstring s = [0x0000FEFF,'T', 'e', 's', 't', 'i', 'n', 'g', ' ', 'U', 'T', 'F', '3', '2'];
    assert(skipBom(s) == "Testing UTF32");
}