C程序的結(jié)構(gòu)實用_第1頁
C程序的結(jié)構(gòu)實用_第2頁
C程序的結(jié)構(gòu)實用_第3頁
C程序的結(jié)構(gòu)實用_第4頁
C程序的結(jié)構(gòu)實用_第5頁
已閱讀5頁,還剩42頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)

文檔簡介

會計學1C程序的結(jié)構(gòu)實用

塊作用域又稱局部作用域。由一對花括號“{}”所括起來的塊中聲明的標識符的作用域從聲明處開始,一直到塊結(jié)束的花括號為止。例如:

#include<iostream.h> voidmain(){ voidfun1(); intn; for(inti=0;i<5;i++)

{ intm; if(i%2)n++; } m=n/2; //錯誤,m未定義

n=i; fun1(); //fun1()函數(shù)調(diào)用

}2)塊作用域第1頁/共47頁voidfun1(){cout<<"i="<<i<<endl; //錯誤,i未定義

}編譯時,函數(shù)fun1()中的語句:

cout<<"i="<<i<<endl;將出現(xiàn)一個未定義錯誤,這是因為塊作用域不能延伸到子函數(shù)中。第2頁/共47頁3)文件作用域#include<iostream.h>

intk;

voidmain() { k=5;{k++;} {intk=7;k++;cout<<"k="<<k;} cout<<“,k="<<k<<endl; }

程序運行結(jié)果為:k=8,k=6可見性遵循的一般規(guī)則:(1)標識符在引用前必須先聲明。(2)在互相沒有包含關(guān)系的不同作用域中聲明同名的標識符時,兩標識符互不影響。(3)如果在兩個或多個具有包含關(guān)系的作用域中聲明了同名標識符,則外層標識符在內(nèi)層不可見。第3頁/共47頁1)靜態(tài)生存期 靜態(tài)生存期與程序的運行期相同。具有文件作用域的變量具有靜態(tài)生存期。如果要在函數(shù)內(nèi)部的塊作用域中聲明具有靜態(tài)生存期的變量,則要使用關(guān)鍵字static。例如:staticintk;

具有靜態(tài)生存期的變量,也稱為靜態(tài)變量。2)局部生存期 在塊作用域中聲明的變量具有局部生存期。此生存期誕生于聲明點,而終止于其作用域的結(jié)束處。具有局部生存期的變量都具有塊作用域。但當在塊作用域內(nèi)將變量說明為靜態(tài)變量時,該變量則具有靜態(tài)生存期。3)動態(tài)生存期 動態(tài)生存期由程序中特定的函數(shù)(malloc()和free())調(diào)用或由操作符(new和delete)創(chuàng)建和釋放。具有動態(tài)生存期的變量在內(nèi)存的堆區(qū)分配空間。2.生存期第4頁/共47頁3.局部變量和全局變量1)局部變量 局部變量包括自動(auto)變量、內(nèi)部靜態(tài)(static)變量和函數(shù)參數(shù)。2)全局變量 全局變量具有文件作用域。

第5頁/共47頁//EX5_1.cpp:演示局部變量和全局變量#include<iostream.h>inti=1; //全局變量i:靜態(tài)生存期voidmain(){staticinta; //聲明局部靜態(tài)變量a:靜態(tài)生存期

intb=-10; //聲明局部變量b:局部生存期

intc=0; //聲明局部變量c:局部生存期

voidother(void); //聲明函數(shù)other()cout<<“main:"<<"i="<<i<<"a="<<a<<"b="<<b<<"c="<<c<<endl;c=c+8;

other(); //調(diào)用函數(shù)other()cout<<“main:"<<"i="<<i<<"a="<<a<<"b="<<b<<"c="<<c<<endl;

other(); //調(diào)用函數(shù)other()}第6頁/共47頁voidother(void){staticinta=1; //局部靜態(tài)變量a:靜態(tài)生存期

staticintb; //局部靜態(tài)變量b:靜態(tài)生存期

intc=5; //局部變量c:局部生存期

i=i+2;a=a+3;c=c+5;cout<<"other:"<<"i="<<i<<"a="<<a<<"b="<<b<<"c="<<c<<endl;b=a;}

程序運行結(jié)果為:

main:i=1a=0b=-10c=0 other:i=3a=4b=0c=10 main:i=3a=0b=-10c=8 other:i=5a=7b=4c=10第7頁/共47頁

靜態(tài)成員為同類的所有對象共同擁有,用于解決同類對象之間數(shù)據(jù)和函數(shù)的共享問題。靜態(tài)成員分為靜態(tài)數(shù)據(jù)成員和靜態(tài)函數(shù)成員。

(1)靜態(tài)數(shù)據(jù)成員聲明:staticintn(2)靜態(tài)數(shù)據(jù)成員必須要在類外進行初始化,初始化的形式為:

<類型標識符><類名>::<靜態(tài)數(shù)據(jù)成員名>=<值>

例如:intPoint::n=0;(3)靜態(tài)成員屬于類,而不屬于任何一個對象;

(4)靜態(tài)成員一樣要服從訪問控制限制;

(5)私有靜態(tài)數(shù)據(jù)成員只能在類內(nèi)引用,公有或保護靜態(tài)數(shù)據(jù)成員可以在類外通過類名引用。

(6)靜態(tài)函數(shù)成員可以直接引用該類的靜態(tài)成員,但不能直接引用非靜態(tài)數(shù)據(jù)成員;

(7)公有靜態(tài)函數(shù)成員可以通過類名或?qū)ο竺麃碚{(diào)用。5.1.2靜態(tài)成員第8頁/共47頁//EX5_2.cpp:演示使用靜態(tài)成員#include<iostream.h>classpoint{private:intx,y; staticintcountP; //聲明私有靜態(tài)數(shù)據(jù)成員

public:point(intxx=0,intyy=0) //定義構(gòu)造函數(shù)

{x=xx;y=yy;countP++;}point(point&p); //聲明拷貝構(gòu)造函數(shù)

intget_x(){returnx;}intget_y(){returny;}staticvoidget_c()

//定義公有靜態(tài)函數(shù)成員

{cout<<“Objectid=”<<countP<<endl;}//私有靜態(tài)數(shù)據(jù)成};//員在類內(nèi)引用第9頁/共47頁point::point(point&p) //定義拷貝構(gòu)造函數(shù){x=p.x; y=p.y;

countP++; //私有靜態(tài)數(shù)據(jù)成員在類內(nèi)引用}intpoint::countP=0; //靜態(tài)數(shù)據(jù)成員必須要在類外初始化voidmain(){point::get_c(); //第1次通過類名調(diào)用靜態(tài)函數(shù)成員

pointa(4,5); //聲明類的對象acout<<"pointa,"<<a.get_x()<<","<<a.get_y();a.get_c(); //第2次通過對象名調(diào)用靜態(tài)函數(shù)成員

pointb(a);cout<<"pointb,"<<b.get_x()<<","<<b.get_y();point::get_c(); //第3次通過類名調(diào)用靜態(tài)函數(shù)成員}第10頁/共47頁

在主函數(shù)中,分別采用類名和對象名來調(diào)用get_c()。第1次調(diào)用get_c()時由于還沒有任何對象生成,只能采用類名的形式。由此可見,通過類名調(diào)用靜態(tài)函數(shù)成員可以輸出靜態(tài)數(shù)據(jù)成員的初始值。后面的2次get_c()的調(diào)用既可以采用類名的形式,也可以采用對象名的形式。

程序運行結(jié)果為:

Objectid=0 pointa,4,5Objectid=1 pointb,4,5Objectid=2第11頁/共47頁//演示使用靜態(tài)成員#include"iostream.h"#include"string.h"classstu{private:char*name,*num; staticinttotal; public: stu(char*,char*); ~stu(); voidprint(); staticintgettotal(){returntotal;}};第12頁/共47頁intstu::total=0;stu::stu(char*n1,char*n2)/*拷貝構(gòu)造函數(shù)怎么設(shè)計?*/{name=newchar[strlen(n1)+1];num=newchar[strlen(n2)+1];strcpy(name,n1);strcpy(num,n2);++total;}voidstu::print(){ cout<<"\nname:"<<name <<"\nnum:"<<num <<"\ntotal:"<<total<<endl;}第13頁/共47頁stu::~stu(){ delete[]name; delete[]num; --total;}intmain(intargc,char*argv[]){stua("wang","000001"); stub("yang","000002"); stuc("tang","000003"); a.print();

cout<<endl<<"total:"<<a.gettotal()<<endl; b.print(); cout<<endl<<"total:"<<stu::gettotal()<<endl; return0;}第14頁/共47頁

聲明友元函數(shù)是為了使普通函數(shù)或其它類的成員函數(shù)能訪問本類的成員,友元函數(shù)在類聲明中由關(guān)鍵字friend修飾。 普通函數(shù)聲明為友元函數(shù)的形式:

friend<類型標識符><友元函數(shù)名>(參數(shù)表)

其它類的成員函數(shù)聲明為友元函數(shù)的形式:

friend<類型標識符><類名>::<友元函數(shù)名>(參數(shù)表)

說明:

(1)友元函數(shù)的聲明可以在類聲明中的任何位置,既可在public區(qū),也可在protected區(qū),意義完全一樣。

(2)友元函數(shù)的定義一般放在類的外部,最好與類的其他成員函數(shù)定義放在一起。5.1.3友元

1.友元函數(shù)第15頁/共47頁//EX5_3.cpp:演示使用普通函數(shù)作友元函數(shù)計算兩點距離

#include<iostream.h>#include<math.h>

classpoint{private: doublex,y;public:point(doublexx=0,doubleyy=0){x=xx;y=yy;}doubleget_x(){returnx;}doubleget_y(){returny;}

frienddoubledistance(pointp1,pointp2);//普通函數(shù)作}; //point的友元第16頁/共47頁doubledistance(pointp1,pointp2)//定義point類的友元函數(shù){return(sqrt((p1.x-p2.x)*(p1.x-p2.x)+(p1.y-p2.y)*(p1.y-p2.y)));}voidmain(){pointmyp1(1,1),myp2(4,5);//聲明point類對象myp1和myp2cout<<"Thedistanceis:"<<distance(myp1,myp2)<<endl;}友元函數(shù)必須先接收對應類的對象,然后通過接收到的對象訪問其所以成員第17頁/共47頁

如果友元是一個類,則稱為友元類。友元類的聲明形式為:

friendclass<友元類名>說明:

(1)友元類的聲明同樣可以在類聲明中的任何位置;

(2)友元類的所有成員函數(shù)都成為友元函數(shù)。

例如,若A類為B類的友元類,即在B類中聲明:

friendclassA;則A類的所有成員函數(shù)都成為B類的友元函數(shù),都可以訪問B類的私有和保護成員。2.友元類第18頁/共47頁

友元類的成員函數(shù)可以通過對象名直接訪問到隱藏的數(shù)據(jù),達到高效協(xié)調(diào)工作的目的。但在使用友元時還有兩點需要注意:(1)

友元關(guān)系不能傳遞。B類是A類的友元,C類是B類的友元,C類和A類之間如果沒有聲明,就沒有任何友元關(guān)系,不能進行數(shù)據(jù)共享。

(2)友元關(guān)系是單向的。如果聲明B類是A類的友元,B類的成員函數(shù)就可以訪問A類的私有和保護數(shù)據(jù),但A類的成員函數(shù)卻不能訪問B類的私有和保護數(shù)據(jù)。第19頁/共47頁例:友元成員函數(shù)#include"string.h"#include"iostream.h"classst_n;classsco{private:intmat,eng;public: sco(inti1,inti2):mat(i1),eng(i2){} voidshow() {cout<<"\nmath:"<<mat; cout<<"\neng:"<<eng; } voidshow(st_n&st);//st_n還沒具體定義,

//函數(shù)show()在后面實現(xiàn)};第20頁/共47頁classst_n{private:char*name,*num;public:

friendvoidsco::show(st_n&); st_n(char*n1,char*n2) {name=newchar[strlen(n1)+1]; num=newchar[strlen(n2)+1]; strcpy(name,n1); strcpy(num,n2); }};第21頁/共47頁voidsco::show(st_n&st){ cout<<"\nname:"<<; cout<<"\nnum:"<<st.num; show();}intmain(intargc,char*argv[]){ st_na("wang","123456"); scob(72,82); b.show(a); return0;}第22頁/共47頁

使用const關(guān)鍵字聲明的引用稱為常引用,常引用所引用的對象不能被更新。用常引用做形參,不會發(fā)生對實參意外的更改。常引用的聲明形式為

const<類型標識符>&<引用名>

注意:常引用的值不能被更新,所以常引用聲明時,必須同時進行初始化。5.1.4常類型

1.常引用第23頁/共47頁//EX5_4.cpp:演示常引用做形參

#include<iostream.h>voiddisplay(constdouble&r);//常引用做形參{cout<<“r=”<<++r<<endl;}//錯誤:更改常引用的對象rvoidmain(){doubled(6.5);display(d);}

這段程序編譯時有一個錯誤:

errorC2166:1-valuespecifiesconstobject。如果將display函數(shù)的定義語句改為:cout<<"r="<<r<<endl;

則得程序運行結(jié)果為:r=6.5第24頁/共47頁

使用const關(guān)鍵字聲明的對象稱為常對象。常對象的聲明形式為const<類名><對象名>

或<類名>const<對象名>

聲明常對象的同時,也要進行初始化,而且該對象以后不能再被更新。3.常成員函數(shù) 使用const關(guān)鍵字聲明的函數(shù)稱為常成員函數(shù),常成員函數(shù)聲明的形式為

<類型標識符><函數(shù)名>(參數(shù)表)const;2.常對象第25頁/共47頁

說明:

(1)const是加在函數(shù)聲明后面的類型修飾符,它是函數(shù)類型的一個組成部分,因此在實現(xiàn)部分也要帶const關(guān)鍵字。

(2)const關(guān)鍵字可以被用于對重載函數(shù)的區(qū)分,例如,可以在類中這樣聲明:

voidfun(); voidfun()const;

(3)常成員函數(shù)不能更新對象的數(shù)據(jù)成員,也不能調(diào)用該類中沒有用const修飾的成員函數(shù)。

(4)常對象只用于調(diào)用它的常成員函數(shù),而不能調(diào)用其他成員函數(shù)。第26頁/共47頁//EX5_5.cpp:演示常成員函數(shù)#include<iostream.h>classA{private: intx,y;public: A(inti=0,intj=0){x=i;y=j;}

voidfun() //定義普通成員函數(shù)

{cout<<"成員函數(shù):x="<<x<<",y="<<y<<endl;}

voidfun()

const

//定義常成員函數(shù)

{cout<<"常成員函數(shù):x="<<x<<",y="<<y<<endl;}};voidmain(){Aobj1(1,2); //聲明普通對象obj1

obj1.fun(); //調(diào)用普通成員函數(shù)

constAobj2(3,4); //聲明常對象obj2

obj2.fun();

//調(diào)用常成員函數(shù)}第27頁/共47頁

程序運行結(jié)果為: 成員函數(shù):x=1,y=2

常成員函數(shù):x=3,y=44.常數(shù)據(jù)成員常數(shù)據(jù)成員也用關(guān)鍵字const說明,常數(shù)據(jù)成員(包括常引用、常對象)由于不能被更新,因此只能用成員初始化列表的方式通過構(gòu)造函數(shù)進行初始化。第28頁/共47頁//EX5_6.cpp:演示常數(shù)據(jù)成員#include<iostream.h>classA{private:

constintx; //常數(shù)據(jù)成員x

staticconstinty; //靜態(tài)常數(shù)據(jù)成員ypublic:

constint&r; //常引用rA(inti):x(i),r(x){} //x和r用初始化列表獲得初值

voidfun() {cout<<"x="<<x<<",y="<<y<<",r="<<r<<endl;}};constintA::y=5; //y的初始化在類外進行第29頁/共47頁voidmain(){Aobj1(1),obj2(2);obj1.fun();obj2.fun();}程序運行結(jié)果為:x=1,y=5,r=1x=2,y=5,r=2第30頁/共47頁

大型程序通常由多個文件組成一個項目(Project),理由是:1.將相關(guān)類和函數(shù)放在一個特定的文件中,對不同的文件進行單獨編寫、編譯,最后再鏈接,避免重復勞動,提高工作效益。2.便于團隊開發(fā)。按邏輯功能將程序分解成多個源文件,使程序容易管理,便于程序員的任務安排。大型程序基本上由三個部分構(gòu)成:類的聲明:通常做成.h文件(HeaderFiles)類成員的實現(xiàn):通常做成.cpp文件(SourceFiles)主函數(shù):通常做成.cpp文件(SourceFiles)5.1.5多文件結(jié)構(gòu)第31頁/共47頁5.2動態(tài)內(nèi)存分配5.2.1new運算符

new運算符用于動態(tài)分配一塊內(nèi)存空間。使用形式為:

指針變量=new<數(shù)據(jù)類型>[長度]例如分配一個可以容納256個char型數(shù)據(jù)的空間:

char*Cbuffer=newchar[256];

使用new運算符時,需要注意:(1)如果分配的空間長度為1個單位,則可以省略[]和其中的整數(shù),例如:

float*pNum=newfloat;與

float*pNum=newfloat[1];等價。第32頁/共47頁(2)使用new運算符分配內(nèi)存空間時,其空間長度可以是變量,也可以是數(shù)值表達式,例如分配一個可以容納10個int型數(shù)據(jù)的空間:

intnSize=5; int*nPInt=newint[nSize+5];

(3)由new分配的內(nèi)存空間是連續(xù)的,可以通過指針的變化訪問所分配空間的每一個元素,例如:

int*nPInt=newint[10]; nPInt[5]=100;

或 *(nPInt+5)=100;(4)如果當前存儲器無足夠的內(nèi)存空間可分配,則new運算符返回0(NULL)。第33頁/共47頁

由new運算符分配的內(nèi)存空間在使用完畢后應該使用delete運算符釋放。delete運算符的使用有兩種形式:

delete指針或

delete[]指針例如:int*pInt=newint; deletepInt; int*pManyInt=newint[10]; delete[]pManyInt;使用delete運算符時,需要注意:(1)用new運算符獲得的內(nèi)存空間,只許使用一次delete,不允許多次對同一塊空間進行多次釋放,否則將會產(chǎn)生嚴重錯誤。(2)delete只能用來釋放由new運算符分配的動態(tài)內(nèi)存空間,不得使用delete運算符去釋放程序中的變量、數(shù)組的存儲空間。5.2.2delete運算符第34頁/共47頁1.鏈表概述 鏈表是一種動態(tài)數(shù)據(jù)結(jié)構(gòu),它的特點是用一組任意的存儲單元(可以是連續(xù)的,也可以是不連續(xù)的)存放數(shù)據(jù)元素。一個簡單的鏈表具有下圖所示的結(jié)構(gòu)形式。5.2.3動態(tài)內(nèi)存分配的應用實例

定義單鏈表結(jié)構(gòu)的最簡單形式為:

structNode

{intdata;Node*next;

};第35頁/共47頁

定義一個鏈表類List,其中包含鏈表結(jié)點的插入、刪除、訪問等功能的成員函數(shù),以便對鏈表進行操作。classList{Node*head; //聲明一個鏈表結(jié)構(gòu)指針

public:List(){head=NULL;} voidInsertList(intaData,intbData);//鏈表結(jié)點的插入

voidDeleteList(intaData); //鏈表結(jié)點的刪除

voidOutputList(); //鏈表結(jié)點的訪問

Node*Gethead(){returnhead;}};第36頁/共47頁voidList::OutputList() //鏈表結(jié)點的訪問{Node*current=head; //建立鏈表頭指針

while(current!=NULL) //如果鏈表存在,

{cout<<current->data<<“”; //顯示鏈表結(jié)點的數(shù)據(jù)

current=current->next; //指向下一個結(jié)點

}cout<<endl;}3.鏈表結(jié)點的插入 如果要將新結(jié)點b插入到鏈表的結(jié)點a之前,則需要考慮下列幾種情況:2.鏈表結(jié)點的訪問第37頁/共47頁(1)插入前鏈表是一個空表,插入新結(jié)點b后,鏈表如圖(a)所示。(2)若a是鏈表的第一個結(jié)點,插入新結(jié)點b后成為第一個結(jié)點,如圖

(b)所示。(3)若a不是鏈表的第一個結(jié)點,則要先找出a的上一個結(jié)點ak,然后新結(jié)點b插到結(jié)點ak

與a之間,如圖(c)所示。(4)若鏈表中不存在a,則新結(jié)點b插在最后,如圖

(d)所示。

第38頁/共47頁//設(shè)aData是結(jié)點a中的數(shù)據(jù),bData是新結(jié)點b中的數(shù)據(jù)voidList::InsertList(intaData,intbData){Node*p,*q,*s;s=(Node*)newNode;//動態(tài)分配一個新結(jié)點存儲區(qū)

s->data=bData; //將新結(jié)點b的數(shù)據(jù)放入新存儲區(qū)

p=head; //結(jié)點指針p指向鏈表頭

if(head==NULL) //若是空表,

{ head=s; //將新存儲區(qū)的地址賦給表頭,即使

s->next=NULL; //新結(jié)點b作為第一個結(jié)點

} else //若不是空表

if(p->data==aData)

//若a是第一個結(jié)點

{

head=s;

//使新結(jié)點b作為第一個結(jié)點

s->next=p;

//將結(jié)點a接到新結(jié)點b的后面

}第39頁/共47頁

else //若a不是第一個結(jié)點

{

while(p->data!=aData&&p->next!=NULL)//找結(jié)點a { q=p; //使q指向p所指的結(jié)點

p=p->next; //

p本身指向下一個結(jié)點

}

if(p->data==aData) //若有結(jié)點a,則q指向的是ak { q->next=s; //將新結(jié)點b插入結(jié)點ak之后

s->next=p; //將結(jié)點a排在新結(jié)點b之后

}else //若沒有結(jié)點a { p->next=s; //將新結(jié)點b排在鏈表末尾,即

s->next=NULL; //將新存儲區(qū)排在鏈表末尾。

}

}}第40頁/共47頁

要在鏈表中刪除結(jié)點a,并釋放被刪除的結(jié)點所占的存儲空間,需要考慮下列幾種情況:(1)若要刪除的結(jié)點a是第一個結(jié)點,則把head指向a的下一個結(jié)點,如圖

(a)所示。(2)若要刪除的結(jié)點a不是第一個結(jié)點,則應使a的上一結(jié)點ak-1的指針域指向a的下一個結(jié)點ak+1,如圖

(b)所示。(3)若空表或要刪除的結(jié)點a不存在,則不作任何改變。4.鏈表結(jié)點的刪除第41頁/共47頁//設(shè)aData是要被刪除結(jié)點a中的數(shù)據(jù)成員voidList::DeleteList(intaData){Node*p,*q;p=head;if(p==NULL)return; //若p為空,則返回

if(p->data==aData) //若a是第一個結(jié)點

{head=p->next; //鏈表頭指向下一個結(jié)點

deletep; //刪除結(jié)點a

}

else //若a不是第一個結(jié)點

{第42頁/共47頁

while(p->data!=aData&&p->next!=NULL)//找結(jié)點a

{q=p; //使q指向p所指的結(jié)點

p=p->next; //

p本身指向下一個結(jié)點

}

if(p->data==a

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責。
  • 6. 下載文件中如有侵權(quán)或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

最新文檔

評論

0/150

提交評論