項目名稱:C++網上圖書訂購系統
目錄:
前言
項目介紹
項目流程圖
項目類圖
重點函數的剖析
流程演示
源代碼、注釋及出處
前言:
1、這是軟件工程綜合實踐專題第一次作業所寫的博客,也是我第一次嘗試編寫博客,如有不足之處還請在評論中指出。
2、我完成作業的順序是:閱讀代碼並添加注釋、運行加以理解——>畫項目流程圖與類圖——>做重點函數的剖析(與博客書寫順序略有不同)。
3、編寫此博客的心得:我通過此次作業嘗試養成閱讀他人程序的能力;並且熟練掌握了一些c++的基本語法,和運用一些數據結構的知識;增進了自己查閱資料、畫流程圖與類圖、編寫博客的能力。以后也會多多嘗試編寫博客。
4、代碼出處:來自本校信院李倩倩同學大一時所編的程序。
項目介紹:
圖書訂購系統是一個簡易的系統,主要為了讓圖書能在c語言程序中存儲信息,根據不同的用戶權限能實現不同的功能。
項目流程圖:

項目類圖:
一:重載運算符並且自定義string數據類型方便使用

二:核心類book類
book類主要是完成對book類的定義以及存儲結構。

三:buyer類
buyer類主要是對購買者的信息結構的定義。

四:訂單類
訂單類主要是對於購買訂單相關函數的調用。

重點函數的剖析:
一、void operator=(const mystring& Str);

2.operator的使用
operator是C++的關鍵字,它和運算符一起使用,表示一個運算符函數,理解時應將operator=整體上視為一個函數名。
這是C++擴展運算符功能的方法,雖然樣子古怪,但也可以理解:一方面要使運算符的使用方法與其原來一致,另一方面擴展其功能只能通過函數的方式(c++中,“功能”都是由函數實現的)。
3.void *memcpy(void *dest, const void *src, size_t n);
memcpy是memory copy的縮寫,意為內存復制,在寫C語言程序的時候,我們常常會用到它。
它的功能是從src的開始位置拷貝n個字節的數據到dest。如果dest存在數據,將會被覆蓋。memcpy函數的返回值是dest的指針。memcpy函數定義在string.h頭文件里。
二、int order::wfile()||int order::rfile()

1.C語言文件操作
1.1 打開文件
FILE *fp = fopen("要點一","要點二");
要點一:
這里可以寫單獨的文件名,比如說“1.txt”,那么他就會在當前c文件的文件夾目錄下查詢文件是否存在,存在則返回這個文件的指針,不存在的話則返回NULL,
這里也可以寫一個文件的絕對路徑,比如說“C:\aaa\ccc\a.txt”這樣的話他就會在整個電腦里面找這個路徑是否存在該文件,存在則返回文件指針,不存在則返回NULL。
要點二:
這里寫的是打開文件之后想要操作的類型主要的類型我查了一下,有如下幾種:
“r”.為讀而打開文本文件.(不存在則出錯)
“w”.為寫而打開文本文件.(若不存在則新建,反之,則從文件起始位置寫,原內容將被覆蓋)
“a”.為在文件后面添加數據而打開文本文件.(若不存在,則新建;反之,在原文件后追加)
“r+”.為讀和寫而打開文本文件.(讀時,從頭開始;在寫數據時,新數據只覆蓋所占的空間,其后不變)
“wb”.為寫而打開二進制文件
“rb”.為讀而打開二進制文件
“ab”.為在文件后面添加數據而打開一個二進制文件
“rb+”.為讀和寫而打開二進制文件.只是在隨后的讀寫時,可以由位置函數設置讀和寫的起始位置
“w+”.首先建立一個新文件,進行寫操作,隨后可以從頭開始讀.(若文件存在,原內容將全部消失)
“a+”.功能與”a”相同;只是在文件尾部添加新的數據后,可以從頭開始讀
“wb+”.功能與”w+”同.只是在隨后的讀寫時,可以由位置函數設置讀和寫的起始位置
“ab+”.功能與”a+”相同;只是在文件尾部添加新數據之后,可以由位置函數設置開始讀的起始位置。
1.2 將數據存入文件(寫文件)
幾種操作函數:
fputc(FILE* fp,int c); //將一字節數據寫入文件,寫入成功返回c,失敗則返回-1
fputs(const char* a,FILE* fp); //將字符數組的指針或者動態申請的數組頭指針指向的數據寫入文件,寫入成功則返回這個數組的頭指針
fprintf(FILE* fp,const char* c,….); //比printf多了一個文件指針的形參,所以說這個函數不是講數據輸出到黑色控制台的,而是輸出到文件中
1.3 關閉文件指針
寫完之后一定莫忘關閉文件指針
fclose(fp);
流程演示:











源代碼及注釋:
代碼出處:來自本校信院李倩倩同學大一時所編的程序。
1 #include<iostream> 2 #include<fstream> 3 #include<string> 4 #include"string.h" 5 using namespace std; 6 7 class mystring 8 { 9 friend ostream& operator<<(ostream& S,const mystring& Str); //重載<< 10 friend istream& operator>>(istream& S,mystring& Str); //重載>> 11 public: 12 mystring(); 13 mystring(const mystring& Str); 14 void operator=(const mystring& Str); 15 ~mystring(); 16 mystring(char* p); 17 18 short m_Length; //字符串長度 19 char* m_Data; //字符串開始地址 20 }; 21 mystring::mystring() 22 { 23 m_Length=1; 24 m_Data=new char [m_Length]; 25 memcpy(m_Data,"",m_Length); 26 }; 27 mystring::mystring(const mystring& Str) 28 { 29 m_Length=Str.m_Length; 30 m_Data=new char [m_Length]; 31 memcpy(m_Data,Str.m_Data,m_Length); 32 }; 33 mystring::mystring(char*p) 34 { 35 m_Length=strlen(p)+1; 36 m_Data=new char [m_Length]; 37 memcpy(m_Data,p,m_Length); 38 }; 39 void mystring::operator=(const mystring& Str) 40 { 41 if (&Str!=this) 42 {delete []m_Data; 43 m_Length=Str.m_Length; 44 m_Data=new char [m_Length]; 45 memcpy(m_Data,Str.m_Data,m_Length); 46 } 47 return; 48 }; 49 mystring::~mystring() 50 {delete[]m_Data; 51 }; 52 ostream& operator<<(ostream& S,const mystring& Str) 53 { 54 short i; 55 for(i=0;i<Str.m_Length-1;i++) 56 S<<Str.m_Data[i]; 57 return S; 58 }; 59 istream& operator>>(istream& S,mystring& Str) 60 {const short BUFLEN=256; 61 char Buf[BUFLEN]; 62 memset(Buf,0,BUFLEN); 63 if(S.peek()=='\n') 64 S.ignore(); 65 S.getline(Buf,BUFLEN,'\n'); 66 Str=Buf; 67 return S; 68 }; 69 //buy.h文件開始 70 class buyer{ 71 protected: 72 string name; 73 int buyerID; 74 string address; 75 double pay; 76 public: 77 buyer(); 78 buyer(string n,int b,string a,double p);//n,b,p分別為姓名,ID,地址 79 string getbuyname(); 80 string getaddress(); 81 double getpay(); 82 int getid(); 83 virtual void display()=0; 84 virtual void setpay(double=0)=0; 85 }; 86 class member:public buyer{ 87 int leaguer_grade; 88 public: 89 member(string n,int b,int l,string a,double p):buyer(n,b,a,p) 90 {leaguer_grade=1;} 91 void display(); 92 void setpay(double p); 93 }; 94 class honoured_guest:public buyer 95 { 96 double discount_rate; 97 public: 98 honoured_guest(string n,int b,double r,string a,double p):buyer(n,b,a,p) 99 {discount_rate=r;} 100 void display(); 101 void setpay(double p); 102 }; 103 class layfolk:public buyer{ 104 public: 105 layfolk(string n,int b,string a,double p):buyer(n,b,a,p) 106 { } 107 void display(); 108 void setpay(double p); 109 }; 110 buyer::buyer() 111 { 112 name=""; 113 buyerID=0; 114 address=""; 115 pay=0; 116 } 117 buyer::buyer(string n,int b,string a,double p){ 118 name=n; 119 buyerID=b; 120 address=a; 121 pay=p; 122 } 123 double buyer::getpay() 124 {return pay;} 125 string buyer::getaddress() 126 {return address;} 127 string buyer::getbuyname() 128 {return name;} 129 int buyer::getid() 130 {return buyerID;} 131 void member::display(){ 132 cout<<"購書人姓名:"<<name<<"\t"; 133 cout<<"購書人編號:"<<buyerID<<"\t"; 134 cout<<"購書人為會員,級別:"<<leaguer_grade<<"\n"; 135 cout<<"地址:"<<address<<"\n"; 136 } 137 void member::setpay(double p){ 138 if(leaguer_grade==1) 139 pay=.95*p+pay; 140 else if(leaguer_grade==2) 141 pay=.90*p+pay; 142 else if(leaguer_grade==3) 143 pay=.85*p+pay; 144 else if(leaguer_grade==4) 145 pay=.8*p+pay; 146 else if(leaguer_grade==5) 147 pay=.7*p+pay; 148 else 149 cout<<"級別錯誤!"; 150 } 151 void honoured_guest::display(){ 152 cout<<"購書人姓名:"<<name<<"\t"; 153 cout<<"購書人編號:"<<buyerID<<"\t"; 154 cout<<"購書人為貴賓!,折扣率為:"<<discount_rate*100<<"%\n"; 155 cout<<"地址:"<<address<<"\n\n"; 156 } 157 void honoured_guest::setpay(double p) 158 {pay=pay+(1-discount_rate)*p;} 159 void layfolk::display(){ 160 cout<<"購書人姓名:"<<name<<"\t"; 161 cout<<"購書人編號:"<<buyerID<<"\t"; 162 cout<<"購書人為普通人:"<<"\n"; 163 cout<<"地址:"<<address<<"\n\n"; 164 } 165 void layfolk::setpay(double p) 166 {pay=pay+p;} 167 //buy.h文件結束 168 169 //book.h文件開始 170 class book{ 171 protected: 172 string book_ID; 173 string book_name; 174 string author; 175 string publishing; 176 double price; 177 public: 178 book(); 179 book(string b_id,string b_n,string au,string pu,double pr); 180 void display(); 181 string getbook_ID(); 182 string getbook_name(); 183 string getauthor(); 184 string getpublishing(); 185 double getprice(); 186 }; 187 book::book(string b_id,string b_n,string au,string pu,double pr){ 188 book_ID=b_id; 189 book_name=b_n; 190 author=au; 191 publishing=pu; 192 price=pr; 193 } 194 book::book(){ 195 book_ID=""; 196 book_name=""; 197 author=""; 198 publishing=""; 199 price=0; 200 } 201 //顯示書本對象書號,書名,作者,出版社和價格 202 void book::display(){ 203 cout<<"書號"<<book_ID<<"\t"; 204 cout<<"書名"<<book_name<<"\t"; 205 cout<<"作者"<<author<<"\n"; 206 cout<<"出版社"<<publishing<<"\t"; 207 cout<<"定價"<<price<<"\n"; 208 } 209 string book::getbook_ID()//只取書號 210 {return book_ID;} 211 string book::getbook_name() //只取書名 212 {return book_name;} 213 string book::getauthor() //只取作者 214 {return author;} 215 string book::getpublishing()//只取出版社 216 {return publishing;} 217 double book::getprice()//只取價格 218 {return price;} 219 //book.h文件結束 220 221 class order{ 222 private: 223 int b,k;//b用於控制輸入編號的循環,k用於控制圖書數量 224 string ch[50]; 225 public: 226 order(int a);//構造函數,確定一個對象有幾本書 227 int wfile(); //寫文件生成訂單的函數 228 int rfile();//讀取顯示訂單信息 229 }; 230 order::order(int a){ 231 k=a; 232 } 233 int order::wfile(){ 234 ofstream fout("order.txt",ios::app);//文件不存在時自動創建在當前目錄下 235 if(!fout){ //文件打開檢測 236 cout<<"Can not open file\n"; 237 return 1; 238 } 239 cout<<"請依次輸入需要訂購的圖書編號:"; 240 fout<<"所需訂購圖書的數量為:"<<k<<endl; 241 fout<<"所需訂購圖書的編號為:\n"; 242 string ch[50]; 243 for(b=0;b<=k-1;b++){ 244 cin>>ch[b]; 245 fout<<ch[b]<<"\n"; 246 } 247 //fout<<"需付款金額為:"; 248 fout.close(); //文件關閉 249 cout<<"訂單已生成在當前文件目錄下的order中\n"; 250 } 251 int order::rfile(){ 252 ifstream fin("order.txt",ios::in); 253 if(!fin){ //文件打開檢測 254 cout<<"Can not open file\n"; 255 return 1; 256 } 257 char ch; 258 while(fin.get(ch)) 259 cout<<ch; 260 fin.close(); 261 cout<<"\n"; 262 } 263 void menu_2() 264 { 265 cout<<"****登錄成功!****\n";} 266 void menu_1(){ 267 int p; 268 string name,ID,code,address; 269 cout<<"\n\t********************\n"; 270 cout<<"\t** 0.注冊 **\n"; 271 cout<<"\t** 1.直接登錄 **\n"; 272 cout<<"\t********************\n"; 273 cout<<"請輸入數字:"; 274 cin>>p; 275 if(p==0){cout<<"請輸入姓名:"; 276 cin>>name; 277 cout<<"請輸入賬號:"; 278 cin>>ID; 279 cout<<"請輸入密碼:"; 280 cin>>code; 281 cout<<"請輸入地址:"; 282 cin>>address;} 283 else if(p==1){ 284 cout<<"請輸入賬號:"; 285 cin>>ID; 286 cout<<"請輸入密碼:"; 287 cin>>code;} 288 else{ 289 cout<<"輸入錯誤!請重新輸入!"; 290 } 291 menu_2(); 292 } 293 294 int main(){ 295 int i=0,buyerid,flag; 296 book*c[2]; 297 layfolk b1("林小茶",1,"北京",0); 298 honoured_guest b2("王遙遙",2,.6,"上海",0); 299 member b3("趙紅艷",3,5,"廣州",0); 300 buyer*b[3]={&b1,&b2,&b3}; 301 book c1("7-302-04504-6","C++程序設計","譚浩強","清華",25); 302 book c2("7-402-03388-9","數據結構 ","徐卓群","北大",20); 303 c[0]=&c1; 304 c[1]=&c2; 305 //主菜單 306 int t,n=0,h=0; 307 cout<<"*********歡迎進入網上圖書訂購系統**********\t\t"; 308 menu_1(); 309 cout<<"管理員輸入1,用戶輸入2: ";//界面分類 310 cin>>t; //選擇進入分界面 311 if(t==1){ 312 while(h!=2){ 313 cout<<"*******管理員功能*******"<<endl; 314 cout<<"* 1.新增圖書信息錄入 *"<<endl; 315 cout<<"* 2.退出 *"<<endl; 316 cout<<"************************"<<endl; 317 cout<<"請選擇:\t"; 318 cin>>n; 319 while(n>2){ 320 cout<<"請重新輸入1-2的功能選擇:"; 321 cin>>n;} 322 switch(n){ 323 case 1: {int booknumber; //書本數目的變量 324 cout<<"輸入需要錄入的本數: "; 325 cin>>booknumber; 326 book* r[50]; 327 string b_id,b_n,au,pu; //依次是書號,書名,作者,出版社 328 double pr; //價格 329 ofstream fbookout("book.txt",ios::app);//文件不存在時自動創建在當前目錄下 330 if(!fbookout){ //文件打開檢測 331 cout<<"Can not open file\n"; 332 return 1; 333 } 334 for(i=0;i<booknumber;i++){ 335 cout<<"輸入書號"<<i<<": "; 336 cin>>b_id; 337 cout<<"輸入書名"<<i<<": "; 338 cin>>b_n; 339 cout<<"輸入作者"<<i<<" "; 340 cin>>au; 341 cout<<"輸入出版社"<<i<<": "; 342 cin>>pu; 343 cout<<"輸入價格"<<i<<": "; 344 cin>>pr; 345 book r1(b_id,b_n,au,pu,pr); 346 r[i]=&r1; 347 fbookout<<"\n"<<r[i]->getbook_ID()<<" "<<"《"<<r[i]->getbook_name()<<"》"<<" "<<r[i]->getauthor()<<" "<<r[i]->getpublishing()<<" "<<r[i]->getprice()<<"元"<<"\n"; 348 cout<<"\n"; 349 } 350 break; 351 } 352 case 2:break; 353 } 354 h=n; 355 }//while(h!=2) 356 }//if(t==1) 357 if(t==2){ 358 h=0; 359 n=0; 360 while(h!=5){ 361 cout<<"****************************"<<endl; 362 cout<<"**********購書系統**********"<<endl; 363 cout<<"* 1.購書查詢 *"<<endl; 364 cout<<"* 2.查詢所有圖書信息 *"<<endl; 365 cout<<"* 3.訂購書籍 *"<<endl; 366 cout<<"* 4.優惠信息 *"<<endl; 367 cout<<"* 5.退出 *"<<endl; 368 cout<<"****************************"<<endl; 369 cout<<"請選擇:\t"; 370 cin>>n; 371 while(n>5){ 372 cout<<"請重新輸入1-5的功能選擇:"; 373 cin>>n; 374 } 375 switch(n){ 376 case 1: 377 {cout<<"購書人信息:\n\n"; 378 for(i=0;i<3;i++) 379 b[i]->display(); 380 cout<<"\n圖書信息:\n\n"; 381 for(i=0;i<2;i++) 382 c[i]->display(); 383 cout<<"\n\n請輸入購書人編號:"; 384 cin>>buyerid; 385 flag=0; 386 for(i=0;i<3;i++) 387 if(b[i]->getid()==buyerid){flag=1;break;} 388 if(!flag){cout<<"編號不存在"<<endl;} 389 else 390 { 391 b[i]->setpay(c[0]->getprice()); 392 b[i]->setpay(c[1]->getprice()); 393 cout<<endl<<"購書人需要付費:"<<b[i]->getpay()<<"\n\n"; 394 break; 395 } 396 } 397 case 2:{ 398 ifstream finbook("book.txt",ios::in); 399 if(!finbook){ //文件打開檢測 400 cout<<"Can not open file\n"; 401 return 1; 402 }//if(!finbook){ 403 char ch; 404 while(finbook.get(ch)) 405 cout<<ch; 406 finbook.close(); 407 cout<<"\n"; 408 break; 409 } 410 case 3: 411 { int a;//a用於控制圖書數量 412 cout<<"請輸入需要訂購圖書的數量:"; 413 cin>>a; 414 order bookorder(a); 415 bookorder.wfile();//錄入訂單信息 416 cout<<" 訂單信息為: \n"; 417 bookorder.rfile();//顯示訂單信息} 418 break; 419 } 420 case 4:{ 421 cout<<"\n\n\t\t————————————————————————\n"; 422 cout<<"\t\t 本店優惠說明 \n"; 423 cout<<"\t\t————————————————————————\n"; 424 cout<<"\t\t 會員: 在本網站購書按vip等級進行優惠 \n"; 425 cout<<"\t\t 5級:按照原價的70%收取 \n"; 426 cout<<"\t\t 4級:按照原價的80%收取 \n"; 427 cout<<"\t\t 3級:按照原價的85%收取 \n"; 428 cout<<"\t\t 2級:按照原價的90%收取 \n"; 429 cout<<"\t\t 1級:按照原價的95%收取 \n"; 430 cout<<"\t\t 貴賓顧客: 按特定折扣率進行優惠 \n"; 431 cout<<"\t\t 普通顧客:按原價購買,沒有優惠 \n"; 432 cout<<"\t\t————————————————————————\n\n\n"; 433 break; } 434 }//switch(n) 435 h=n; 436 }// while (h!=5) 437 }//if(t==2) 438 }//int main() 439 //buy_book.cpp文件結束
