需要反省,说好一日一练的,昨天周五就偷懒出去逛了逛。。。吾当一日三省吾身。。。
今天的练习是写一个小程序,需要用到文件的读写,不过越写越长,又用到了很多乱七八糟的内置类什么的,就当是复习了吧,大概涉及到以下几个知识:
enum
fstream
stringstream
vector
渣程序如下:
#include <iostream> #include <fstream> #include <string> #include <sstream> // stringstream会用到 #include <vector> using namespace std; // 用户等级 enum level{ Normal, // 普通用户 Senior, // 高级用户 VIP // VIP用户 }; // 写完了才觉得这里用枚举太坑爹了,输出还要转换,算了,权当复习枚举了 class User { public: string name; level userLevel; private: string password; public: User(string n, level l, string pw):name(n),userLevel(l),password(pw) { } void PrintInfo(); // 在控制台打印 void WriteInfo(string filename); // 写入到文件 }; void User::PrintInfo() { cout << "UserInfo:\n name: " << name << "\n userLevel: "; switch(userLevel) { case Normal: cout << "普通用户\n password: " << password << endl << endl; break; case Senior: cout << "高级用户\n password: " << password << endl << endl; break; case VIP: cout << "VIP用户\n password: " << password << endl << endl; break; default: cout << "普通用户\n password: " << password << endl << endl; } } void User::WriteInfo(string filename) { ofstream file; // 打开一个文件,open第一个参数为const char*,string类型需要做一下转换 // 打开文件的模式为写入,且写入的所有数据将被追加到文件末尾 file.open(filename.c_str(), ios::out|ios::app); if(!file) { cerr << "打开文件 " << filename << "失败!" << endl << endl; } file << name << "\t "; switch(userLevel) { case Normal: file << "普通用户\t " << password << endl; break; case Senior: file << "高级用户\t " << password << endl; break; case VIP: file << "VIP用户\t " << password << endl; break; default: file << "普通用户\t " << password << endl; } file.close(); cout << "录入用户 " << name << " 信息到文件 " << filename << " 成功!" << endl; } void ReadUserFile(string filename, vector<User *> &vec_user) { string userLine; ifstream file; file.open(filename.c_str(), ios::in); while(getline(file, userLine)) { string name; string userLevel; level fuckLevel; // 为毛我之前要用enum。。。越写越坑爹 string password; stringstream userStr(userLine); userStr >> name; userStr >> userLevel; if("高级用户" == userLevel) { fuckLevel = Senior; } else if("VIP用户" == userLevel) { fuckLevel = VIP; } else { fuckLevel = Normal; } userStr >> password; User *tempUser = new User(name, fuckLevel, password); vec_user.push_back(tempUser); } } int main(int argc, char *argv[]) { User user1("adam", Normal, "adam_is_good_girl~"); User user2("john", Senior, "who_is_john?"); User user3("lisa", VIP, "i_don‘t_know_lisa..."); cout << "看一下我们都有哪些用户" << endl; user1.PrintInfo(); user2.PrintInfo(); user3.PrintInfo(); string filename; cout << "请输入文件名:"; cin >> filename; user1.WriteInfo(filename); user2.WriteInfo(filename); user3.WriteInfo(filename); cout << "刚才的用户信息已经被存放在 " << filename << "文件里,赶快去看看吧~!" << endl; vector<User *> vecUser; ReadUserFile(filename, vecUser); cout << "现在从文件里读出来看看" << endl; for(vector<User *>::iterator iter = vecUser.begin(); iter != vecUser.end(); iter++) { (*iter)->PrintInfo(); } return 0; }
输出:
文件读写流fstream到底什么读什么是写?
ofstream是从内存到硬盘,即写入文件用的
ifstream是从硬盘到内存,即读到程序用的
o就是out,i就是in,不过这里需要转换一下思维,out和in是站在程序的角度看的,对于程序来说,out就是写出去,in就是读进来
没有ios::nocreate这个属性了?
这里有一点需要注意,当百度出来fstream用法,在打开方式里有这么一个东西:
ios::nocreate: 不建立文件,所以文件不存在时打开失败
这个我尝试了一下,但是不好用了,据度娘说从VS2003开始,这个就没有了,open 函数默认打开就是不创建文件