Read and write to a text file. HELP

Hey guys! I'm a beginner to c++ and I want to know how I would be able to have a read or write function to a separate file.

I'm creating a launcher for minecraft server which has the ability to edit the config through the console.

I had to throw it all onto one line as I had no clue how to do otherwise, it works but I'm sure there is a neater way such as header files, but I don't know how to use those! hah!

Anyway I just wanted to know if I could get a line from the text file "server.properties" and then have the ability to edit a part of it like:
"hardcore=false"
It will give me the option to change that to true.
Here is the server.properties.

The ability to add custom lines of code to the server.properties at the end of the file would be nice too.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#Minecraft server properties
#Sat Feb 09 15:27:53 GMT 2013
generator-settings=
allow-nether=false
level-name=world
enable-query=false
allow-flight=false
server-port=25565
level-type=DEFAULT
enable-rcon=false
level-seed=
server-ip=
max-build-height=256
spawn-npcs=false
white-list=false
spawn-animals=false
snooper-enabled=true
hardcore=false
texture-pack=
online-mode=true
pvp=false
difficulty=0
gamemode=1
max-players=20
spawn-monsters=false
generate-structures=false
view-distance=10
spawn-protection=16
motd=A Minecraft Server


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
#include <iostream>
#include <string>
#include <fstream>
#include <stdio.h>
#include <time.h>


using namespace std;

int main(){
	int choice;

	system("color 06");
	cout << "Minecraft server!\n";
	cout << "1. Start\n";
	cout << "2. Configure\n";
	cout << "3. Exit\n";
	time_t rawtime;
	struct tm * timeinfo;
    time ( &rawtime );
    timeinfo = localtime ( &rawtime );
	do{

		cin >> choice;

		if (choice == 1){
			system("java -Xms1024M -Xmx1024M -jar craftbukkit.jar -o true");
			system("pause");
		}
		else if (choice == 2){
			ofstream myfile;
			myfile.open ("server.properties");
			myfile << "#Minecraft server properties\n" << "#" << asctime(timeinfo) << endl << "generator-settings=\n" << "allow-nether=false\n" << "level-name=world\n" << "enable-query=false\n" << "allow-flight=false\n" << "server-port=25565\n" << "level-type=DEFAULT\n" << "enable-rcon=false\n" << "level-seed=\n" << "server-ip=\n" << "max-build-height=256\n" << "spawn-npcs=false\n" << "white-list=false\n" << "spawn-animals=false\n" << "snooper-enabled=true\n" << "hardcore=false\n" << "texture-pack=\n" << "online-mode=true\n" << "pvp=false\n" << "difficulty=0\n" << "gamemode=1\n" << "max-players=20\n" << "spawn-monsters=false\n" << "generate-structures=false\n" << "view-distance=10\n" << "spawn-protection=16\n" << "motd=A Minecraft Server\n";
			system("pause");
		}
		else if (choice == 3){
			exit;
		}
		else{
			cout << "Invalid Choice, choose again.\n";
		}
	}while (choice >= 3);
}


Thank you! :D
bump
There are several ways to go about this, you could put the properties
in a 3d array but I think the simplest is to simply dump out the file with
line numbers, give the user a choice of which line to edit. Let them type
in their string, then write the file replacing line X with their string.

This will give you a example how to start.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
#include <iostream>
#include <string>
#include <fstream>
#include <stdio.h>
#include <time.h>


using namespace std;

int main(){
	int choice;

// 	system("color 06");
	cout << "Minecraft server!\n";
	cout << "1. Start\n";
	cout << "2. Create\n";
	cout << "3. Edit\n";
	cout << "0. Exit\n";
	time_t rawtime;
	struct tm * timeinfo;
    time ( &rawtime );
    timeinfo = localtime ( &rawtime );
	do{

		cin >> choice;

		if (choice == 1)
		{
//			system("java -Xms1024M -Xmx1024M -jar craftbukkit.jar -o true");
//			system("pause");
		}
		else if (choice == 2)
		{
			ofstream myfile;
			myfile.open ("server.properties");
			myfile << "#Minecraft server properties\n" << "#" << asctime(timeinfo) << endl << "generator-settings=\n" << "allow-nether=false\n" << "level-name=world\n" << "enable-query=false\n" << "allow-flight=false\n" << "server-port=25565\n" << "level-type=DEFAULT\n" << "enable-rcon=false\n" << "level-seed=\n" << "server-ip=\n" << "max-build-height=256\n" << "spawn-npcs=false\n" << "white-list=false\n" << "spawn-animals=false\n" << "snooper-enabled=true\n" << "hardcore=false\n" << "texture-pack=\n" << "online-mode=true\n" << "pvp=false\n" << "difficulty=0\n" << "gamemode=1\n" << "max-players=20\n" << "spawn-monsters=false\n" << "generate-structures=false\n" << "view-distance=10\n" << "spawn-protection=16\n" << "motd=A Minecraft Server\n";
//			system("pause");
		}
		
		else if (choice == 3)
		{
		cout << "----------" << endl;
		int linetoedit=0;
		string line;
		int linecount=0;
		ifstream myfile;
		myfile.open ("server.properties");
		if (myfile.is_open())
		{
		while (myfile.good())
		{
		getline (myfile,line);
		linecount ++;
		cout << linecount << " " << line << endl;
		}
		cout << "Choose line to edit, 0 to exit : ";
		cin >> linetoedit;
		cout << "Line to edit is " << linetoedit << endl;

		}

		}
		
		
		else if (choice == 0)
		{
//			exit;
		}
		else
		{
			cout << "Invalid Choice, choose again.\n";
		}
	}while (choice >= 3);
}
Last edited on
OK, thank you! It's finally able to print out the lines, now how easy would it be to replace a line, for example. If I chose line 30 how easy would it be to edit it?

EDIT: I meant to say, what functions will I be using as I don't have the faintest idea on how to even begin replacing the lines.
Last edited on
If you know line 30 is always going to be the same

These are just examples, may or may not work without some edits.

1
2
3
4
if (linecount==30)
     {cout << "new string" << endl;
else
     {cout << line << endl;}


If line30 changes, you will have to match the string, such as
1
2
if (line=="hardcore=false")
     {cout << "hardcore=true" << endl;}
Sadly lines in server.properties are not guaranteed to follow any particular order.
I used this class to work with properties:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
//MCServerConfig.h

#ifndef MCSERVERCONFIG_H_INCLUDED
#define MCSERVERCONFIG_H_INCLUDED

#include <string>
#include <unordered_map>

class MCServerProperties
{
private:
    std::unordered_map<std::string,std::string> container;
public:
//    void force_allowed();
    void default_init();
    void read(std::string key);
    void write(std::string key, std::string value);
    void load(std::string file);
    void save(std::string file);


    MCServerProperties();
    MCServerProperties(std::string file);
};

#endif // MCSERVERCONFIG_H_INCLUDED 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
//MCServerConfig.cpp

#include <iostream>
#include <fstream>
#include <string>
#include <unordered_map>
#include <stdexcept>
#include "MCServerConfig.h"
using std::string;

void MCServerProperties::default_init()
{
    container        ["allow-flight"] = "false";
    container        ["allow-nether"] = "true";
    container          ["difficulty"] = "1";
    container        ["enable-query"] = "false";
    container         ["enable-rcon"] = "false";
    container["enable-command-block"] = "false";
    container            ["gamemode"] = "0";
    container ["generate-structures"] = "true";
    container  ["generator-settings"] = "";
    container            ["hardcore"] = "false";
    container          ["level-name"] = "world";
    container          ["level-seed"] = "";
    container          ["level-type"] = "DEFAULT";
    container    ["max-build-height"] = "256";
    container         ["max-players"] = "20";
    container                ["motd"] = "A Minecraft Server";
    container         ["online-mode"] = "true";
    container                 ["pvp"] = "true";
    container          ["query.port"] = "25565";
    container       ["rcon.password"] = "";
    container           ["rcon.port"] = "25575";
    container           ["server-ip"] = "";
    container         ["server-port"] = "25565";
    container     ["snooper-enabled"] = "true";
    container       ["spawn-animals"] = "true";
    container      ["spawn-monsters"] = "true";
    container          ["spawn-npcs"] = "true";
    container    ["spawn-protection"] = "16";
    container        ["texture-pack"] = "";
    container       ["view-distance"] = "10";
    container          ["white-list"] = "false";
}

void MCServerProperties::read(string key)
{
    try {
        std::cout << container.at(key) << std::endl;
    } catch(std::out_of_range) {
        std::cout << "element " << key << " does not exist!" << std::endl;
}   }

void MCServerProperties::write(string key, string value)
{
    try {
        container.at(key) = value;
    } catch(std::out_of_range) {
        std::cout << "element " + key + " does not exist!" << std::endl;
}   }

void MCServerProperties::load(string file)
{
    std::ifstream source(file);
    if(!source.is_open())
        throw std::ios_base::failure("Unable to open file for reading: " +
                                     file);
    string input;
    while(getline(source, input)) {
        if(input[0] == '#')
            continue;
        unsigned int pos(input.find('='));
        if (pos == input.npos)
            continue;
        string name, value;
        name = input.substr(0, pos);
        value = input.substr(pos + 1, input.npos);
        container[name] = value;
}   }

void MCServerProperties::save(string file)
{
    std::ofstream out(file);
    if(!out.is_open())
        throw std::ios_base::failure("Unable to open file for writing: " +
                                     file);
    for(auto o: container)
        out << o.first << '=' << o.second << std::endl;
    out.close();
}

MCServerProperties::MCServerProperties()
{
    default_init();
}

MCServerProperties::MCServerProperties(string file)
{
    default_init();
    load(file);
}

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
//main.cpp (example of use)

#include <iostream>
#include "MCServerConfig.h"
using std::string;

int main()
{
    MCServerProperties config;
    string input;

//Open config file
    std::cout << "Enter the name of the config file: ";
    getline(std::cin, input);
    try {
        config.load(input);
    } catch(std::ios_base::failure x) {
        std::cerr << x.what();
        return -1;
    }
//Allows user to read random parameters
    std::cout << "Enter name of the parameter to see its value,\n" <<
                  "\"!\" to exit" << std::endl;
    while(getline(std::cin, input)) {
        if(input == "!")
            break;
        config.read(input);
    }

//Saving by different name
    config.save("save.txt");
    return 0;
}
Topic archived. No new replies allowed.