替换文件中间的文本

时间:2016-06-20 12:18:26

标签: c++

我有.txt个文件,并且有行:

username1:123456789:etc:etc:etc:etc
username2:1234:etc:etc:etc:etc
username3:123456:etc:etc:etc:etc
username4:1234567:etc:etc:etc:etc

username1 - username; 123456789 - 密码; 等 - 更多文字。

我有代码来读取文件并查找我需要的username行。还有代码更改密码,但是如果新密码比旧密码更长,则会出现问题:

username3:11111111111tc:etc:etc:etc

如果新密码较短,则表示如下:

username1:111111789:etc:etc:etc:etc

我有新密码的长度,但我怎样才能获得旧密码的长度并正确更换?

我的代码

include<iostream>
#include<fstream>
#include <cstring>

using namespace std;

int main() {
    int i=0;
    bool found = false;
    string line, username;
    char newpass[255] = "555555555555555";
    long length, plen;


    cout<<"Insert username: ";
    cin>>username;
    username+=":";
    fstream changeLINE("/.../testaDoc.txt");

    if (!changeLINE) {
        cout << "Can't find the file or directory!" << endl;
    }
    else

        while (getline(changeLINE, line) && !found) {
            i++;

            if (line.find(username) != string::npos) {
                length = changeLINE.tellg();
                changeLINE.seekg((length - line.length()) + username.length() - 1);
                changeLINE.write("", strlen(newpass));
                cout << line << " line " << i << endl;
                found = true;
            }
        }

    if (!found)
        cout << "User with username = " << username << " NOT FOUND!";

    changeLINE.close();

}

我在Linux上工作,用C ++编写。

修改

也许有办法在文本中添加字符串,但不能替换它,也可以通过不替换它来擦除字符串?然后我可以读取旧密码的长度,将其与新密码进行比较,并在字符串中删除/添加字母以正确替换它。

1 个答案:

答案 0 :(得分:0)

除非您要替换的行与新行相同,否则您需要采用不同的策略 -

这是您可以使用的策略:

  • 创建临时文件
  • 将您不想直接更改的行写入临时文件。要更改的行,您将替换为新行
  • 关闭这两个文件。
  • 删除原始文件
  • 将临时文件重命名为原始文件名

或者你可以在评论中提到将所有行读入内存,例如:行向量,替换要更改的行,然后将所有行写回文件,替换以前的内容。如果新行比前一行短,您可以使用例如How to truncate a file while it is open with fstream

来截取文件。

这可行吗?

std::vector<std::string> lines;
while (std::getline(changeLINE, line)) 
{
    i++;

    if (line.find(username) != std::string::npos) {            
        std::cout << line << " line " << i << std::endl;
        found = true;
        std::string newline = username + ":" + newpass +     line.substr(line.find(":", username.length() + 2)) ;
        lines.push_back(newline);
    }
    else
    {
        lines.push_back(line);
    }
}

changeLINE.close();
std::ofstream ofs;
ofs.open("/.../testaDoc.txt", std::ofstream::out | std::ofstream::trunc);

for(auto& s: lines)
    ofs << s << std::endl;

ofs.close();