【问题标题】:Change a text file in random access在随机访问中更改文本文件
【发布时间】:2013-09-01 01:33:33
【问题描述】:

我有一个文本文件,想在某些地方更改它,例如字节范围 4030 到 4060,这样:

  • 如果有字符 'C' 或 'c' 后跟 'G' 或 'g' ,必须改成 'B' 字符

输入文件是一个文本文件,我想获得一个更改后的文本输出文件。文本文件中没有随机访问,因此我必须以二进制形式打开文件并进行更改,但输出文件将是二进制文件,我不知道要获得文本输出。代码如下:

int main()
{
    string str, cstr;
    ReadTextFile("in", 4030, 4060);
    return 0;
}

string ReadTextFile(string path, int from, int to)
{
    fstream fp(path.c_str(), ios::in|ios::out|ios::binary);
    char *target;
    string res, str;
    target = new char[to - from + 1];
    if (!target)
    {
        cout << "Cannot allocate memory." << endl;
        return "";
    }
    fp.seekg(from);
    fp.read(target, to - from);
    target[to - from] = 0;
    res = target;
    str = changestring(res);
    fp.seekg(from);
    fp.write((char *)&str, to-from);
    return res;
}

string changestring(string str)
{
    int l = str.length();
    l = l-1;
    for (int i = 0; i <= l; i++)
    {
        if (str[i] == 'C' ||  str[i] == 'c')
        {
            int j = i+1;
            if (str[j] == 'G' || str[j] == 'g')
                str[i] = 'B';
        }
    }
    return str;
}

【问题讨论】:

  • 这不是所有的代码。我假设有原型可供main() 用于它后面的函数,否则这些都不会首先编译。
  • 在 Unix 上,二进制文件和文本文件之间没有区别,您可以将其打开并使其工作。如果您在其他系统上并将文件作为“文本”文件打开,则 CRLF 在输入时映射到 NL,然后在输出时再次映射,这意味着您必须担心字节范围的含义。
  • 是CG映射到BG的变换吗?还是CG映射到B?有很大的不同,因为第一个是保留长度,而第二个不是。
  • 在许多问题中,如果传递给changestring() 的字符串中的last 字符是'c''C',您的代码块随后会索引一个插槽超出字符串结尾并进入未定义行为的领域。 (感谢乔纳森重新格式化;我可以再次睁开眼睛)。
  • 这些 cmets 都没有解决这个问题,请注意,我无法以文本格式获取更改后的文本文件,这是问题所在。例如,我的一个输出是这样的 AAAAAAAAAAAA(c \E0\00\00\00\00\00X\CCCgCGtcCTCCGGAAAA ,这是一个必须更改的字符串,但现在我有一个文本和二进制形式。

标签: c++ text random binary


【解决方案1】:

您误解了文本和二进制。如果您以二进制模式打开文件,那么输出将是二进制的,这不是真的。实际上,所有二进制模式所做的都是停止在 Windows 系统上将 \n 转换为 \r\n。换句话说,它会影响文本文件中的行尾,仅此而已。

您在输出中得到二进制文件,因为您正在将指向字符串的内部指针写入输出,而是将字符写入文件。

改变

fp.write((char *)&str, to-from);

fp.write(str.c_str(), to-from);

这也可以

fp << str;

要获得文本输出,请编写文本。无论您是使用write 还是使用&lt;&lt;,都没有关系,文本就是文本。不要再考虑二进制和文本两种输出模式了.

【讨论】:

    猜你喜欢
    • 2017-09-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-01-10
    • 1970-01-01
    • 2010-09-17
    • 1970-01-01
    相关资源
    最近更新 更多