day09
#include <iostream>
using namespace std;
class A{
public:
virtual void fooa(int x){
cout << "fooa(int)" << endl;
cout << x << endl;
}
virtual void foob(int x){
cout << "foob(int)" << endl;
cout << x << endl;
}
};
typedef void (*VFUN)(A* mythis, int x);
typedef VFUN* VTABLE;
int main(){
A a;
VTABLE vt=*((VTABLE*)&a);
vt[0](&a,123);
vt[1](&a,123);
}
c++ 的IO
一、c++中的标准对象
cout
cin
cerr
clog
缓冲 flush
cout 可以重定向
cerr clog 不能重定向
#include <iostream>
using namespace std;
int maim(){
cout << "hello";
cerr << "world";
clog << "test";
cout << endl;
}
二、c++ IO类结构图
istream ostream #include<iostream>
ifstream ofstream
fstream #include<fstream>
istringstream ostringstream #include<sstream>
三、格式化IO 和非格式化IO
格式化 有类型的概念
非格式化 没有类型的概念
所有的数据都当成字符来看
四、非格式化
int get(); //EOF
istream& get(char& ch); //只要流变成NULL代表文件 结束
#include <iostream>
using namespace std;
int main(){
int x;
while(1){
x=cin.get();
cout.put(x);
cout << x << endl;
}
}
#include <iostream>
#include <fstream>
using namespace std;
int main(){
int x;
ifstream ifs("1.txt");
x=cin.get();
cout.put(x);
cout << x << endl;
while((x=ifs.get())!= NULL){
cout.put(x);
}
}
/*清空缓冲区 和 流的复位*/
clear() 流的复位
当流出错时 流对象自动变成NULL指针,需要使用clear()才能恢复流。
ignore
/*清理缓冲区中的多少个字符
清理到哪个字符为止*/
istream& ignore( streamsize num=1, int delim=EOF )
#include <iostream>
using namespace std;
int main(){
char data[10];
cout << cin << endl;
cin.getline(data,5);
cout << data << endl;
if(!cin){
cin.clear();
cin.ignore(200,'
');
}
cout << cin << endl;
/*流对象出错自动变成0 拒绝IO*/
int x;
cin >> x;
cout << x << endl;
}
/*回退一个字符*/
istream& putback(char c);
/*查看下一个字符*/
peek();
#include <iostream>
using namespace std;
int main(){
char c;
//cin.get(c);
//cout << "c=" << c <<endl;
//cin.putback(c);
c=cin.peek();
cout << "c=" << c << endl;
string mystr;
cin >> mystr;
cout << mystr <<endl;
}
五、字符串IO
istringstream //数据来源于字符串流对象
ostringstream //把数据写入到字符串
构造函数:
无参的构造函数
有一个string参数的构造函数
运算符
<< >>
成员函数:
string str();
#include <iostream>
#include <sstream>
#include <ctime>
#include <iomanip>
using namespace std;
struct Date{
int year;
int month;
int day;
/*重载Date的输出运算符 就可以使用ostringstream 对象把日期变成字符串
Date date={2014,10,1};
cout << date;*/
};
ostream& operator<<(ostream& os, const Date&n date){
return os << setfill('0') << setw(4)
<< date.year << '-' << setw(2)
<< date.month << '-' << setw(2)
<< date.day;
}
int main(){
string name="tom";
int age=24;
double salary=5500;
ostringstream oss;
oss << name << ' ' << age << ' '
<< salary;
string mystr=oss.str();
cout << mystr << endl;
/* 把当前时间变成字符串*/
time_t t=time(NULL);
struct tm *mytm=localtime(&t);
ostringstream oss2;
oss2 << setfill('0') << mytm->tm_year+1900
<< '-' << setw(2) << mytm->tm_mon+1
<< '-' << setw(2) << mytm->tm_mday
<< ' ' << setw(2) << mytm->tm_hour
<< ':' << setw(2) << mytm->tm_min
<< ':' << setw(2) << mytm->tm_sec
<< "log";
const char* mysctr=oss2.str().c_str();
cout << mysctr << endl;
/*把一个日期对象 变成字符串*/
Date date={2014,7,17};
ostringstream oss3;
oss3 << date;
cout << oss3.str() << endl;
/*istringstream */
istringstream iss();
}
六、文件IO
使用get put 函数复制一个文件
ifstream
ofstream
关闭流 close()
istream& read(char* buffer,streamsize num);
ostream& write(const char* buffer, streamsize num);
streamsize gcount();//最近一次读到的字节数
#include <iostream>
#include <fstream>
using namespace std;
int main(){
ifstream ifs("1.txt");
if(!ifs){
cout << "open failed" << endl;
return -1;
}
ofstream ofs("2.txt");
if(!ofs){
cout << "create failed" << endl;
return -1;
}
char c;
while(ifs.get(c)){
ofs.put(c);
}
ifs.close();
ofs.close();
}
/*把数据读取到一个缓冲区 大小100字符*/
#include <iostream>
#include <fstream>
using namespace std;
int main(){
ifstream ifs("1.txt");
if(!ifs){
cout << "open failed" << endl;
return -1;
}
ofstream ofs("2.txt");
if(!ofs){
cout << "create failed" << endl;
return -2;
}
while(ifs.read(data,100)){
ofs.write(100);
}
int datacount=ifs.gcount();
ofs.write(data,datacount);
ifs.close();
ofs.close();
/*ifstream ifs("1.txt");
char data[400];
ifs.read(data,400);
cout << ifs.gcount() << endl;
cout << ifs << endl;
ifs.read(data,400);
cout << ifs.gcount() << endl;
cout << ifs << endl;*/
}
/*反复打开文件100次 每次写一个整数1-100的数字写入文件*/
#include <iostream>
#include <fstream>
using namespace std;
int main(){
ofstream ofs("2.txt");
if(!ofs){
cout << "create failed" << endl;
return -1;
}
for(int i=1;i<100;i++){
ofs.close();
ofs.open("2.txt",ios::app);
ofs << i << '
';
}
ofs.close();
}
七、随机文件读写
seek(大小,相对参考位置);
相对参考位置
iOS::beg
ios::cur
ios::end
读指针和写指针是同一个
tellp() //得到写位置
tellg() //得到读位置
八、写一个程序 把一个文件中的内容读取出来把每个字符都和一个随机的字符进行^操作
然后吧异或之后的数据写入另一个文件。然后从程序命令行传入一个字符对应的数字 进行解密
#include <iostream>
#include <ctime>
#include <cmath>
#include <cstdlib>
#include <fstream>
using namespace std;
/*对数据进行异或操作*/
void _xor(const char* src,const char* des, unsigned char key){
ifstream ifs(src);
if(!ifs){
cout << "open sec file failed" << endl;
return;
}
ofstream ofs(des);
if(!ofs){
cout << "create des file failed" << endl;
return;
}
char data[100];
while(ifs.read(data,100)){
for(int i=0;i<100;i++){
data[i]^=key;
}
ofs.write(data,100);
}
int datacount=ifs.gcount();
for(int i=0;i<datacount;i++){
data[i]^=key;
}
ofs.write(data,100);
ofs.close();
ifs.close();
}
/*加密函数*/
void encode(const char* src,const char* des){
unsigned char key=rand()%256;
_xor(src,des,key);
cout << "key=" << (int)key << endl;
}
/*解密函数*/
void decode(const char* src,const char* des,unsigned char key){
_xor(src,des,key);
}
int main(int argc, char** argv){
srand(time(NUL));
if(argc < 3){
cout << "程序使用错误 如下使用:" << endl;
cout << "加密:a.out 源文件名 加密文件名" << endl;
cout << "解密:a.out 加密文件名 解密文件名 密钥" << endl;
return -1;
}else if(3==argc){
cout << "加密文件 密钥随机生成" << endl;
encode(argv[1],argv[2]);
}else{
cout << "解密文件" << endl;
decode(argv[1],argv[2],atoi(argv[3]));
}
}