真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

c語(yǔ)言輸出函數(shù)堆棧,c語(yǔ)言棧的函數(shù)

棧的c語(yǔ)言實(shí)現(xiàn)基本操作

寫(xiě)了一個(gè)鏈?zhǔn)綏?,你看?/p>

網(wǎng)站建設(shè)哪家好,找創(chuàng)新互聯(lián)!專注于網(wǎng)頁(yè)設(shè)計(jì)、網(wǎng)站建設(shè)、微信開(kāi)發(fā)、小程序制作、集團(tuán)企業(yè)網(wǎng)站建設(shè)等服務(wù)項(xiàng)目。為回饋新老客戶創(chuàng)新互聯(lián)還提供了印江免費(fèi)建站歡迎大家使用!

# include stdio.h

# include malloc.h

# include stdlib.h

typedef struct Node

{

int data;

struct Node *pNext;

}NODE, *PNODE;

typedef struct Stack

{

PNODE pTop;

PNODE pBottom;//pBottem是指向棧底下一個(gè)沒(méi)有實(shí)際意義的元素

}STACK, *PSTACK;

void init( PSTACK );

void push( PSTACK, int );

void traverse( PSTACK );

int pop( PSTACK, int * );

int empty( PSTACK pS );

int main( void )

{

STACK S;//STACK等價(jià)于struct Stack

int val;

init( S );//目的是造出一個(gè)空棧

push( S, 1 );//壓棧

push( S, 2 );

push( S, 3 );

push( S, 4 );

push( S, 5 );

push( S, 6 );

push( S, 7 );

traverse( S );//遍歷輸出

// clear( S ); //清空數(shù)據(jù)

// traverse( S );//遍歷輸出

if( pop( S, val ) )

{

printf( "出棧成功,出棧的元素是%d\n", val );

}

else

{

printf( "出棧失敗" );

}

traverse( S );//遍歷輸出出棧之后的元素

return 0;

}

void init( PSTACK pS )

{

pS-pTop = ( PNODE )malloc( sizeof( NODE ) );

if( NULL == pS-pTop )

{

printf( "動(dòng)態(tài)內(nèi)存分配失敗!\n" );

exit( -1 );

}

else

{

pS-pBottom = pS-pTop;

pS-pTop-pNext = NULL;//或是pS-pBottom = NULL;

}

}

void push( PSTACK pS, int val )

{

PNODE pNew = ( PNODE )malloc( sizeof( NODE ) );

pNew-data = val;

pNew-pNext = pS-pTop;//pS-Top不能改為pS-pBottom

pS-pTop = pNew;

}

void traverse( PSTACK pS )

{

PNODE p = pS-pTop;

while( p != pS-pBottom )

{

printf( "%d ", p-data );

p = p-pNext;

}

printf( "\n" );

}

int empty( PSTACK pS )

{

if( pS-pTop == pS-pBottom )

return 1;

else

return 0;

}

//把pS所指向的棧出棧一次,并把出棧的元素存入pVal形參所指向的變量中,如果出棧失敗,則返回false,否則true

int pop( PSTACK pS, int *pVal)

{

if( empty( pS ) )//pS本身存放的就是S的地址

{

return 0;

}

else

{

PNODE r = pS-pTop;

*pVal = r-data;

pS-pTop = r-pNext;

free( r );

r = NULL; //為什么要把r賦給NULL呢??

return 1;

}

}

//clear清空

void clear( PSTACK pS )

{

if( empty( pS ) )

{

return ;

}

else

{

PNODE p = pS-pTop;

PNODE q = p-pNext;

while( p != pS-pBottom )

{

q = p-pNext;

free( p );

p = q;

}

pS-pTop = pS-pBottom;

}

}

請(qǐng)用C語(yǔ)言編寫(xiě)一個(gè)堆棧函數(shù)程序

//該程序簡(jiǎn)單并可正確運(yùn)行,希望kutpbpb的回答能對(duì)你有所幫助!

#includestdio.h

#define N 100

typedef struct

{

int value[N];

int base;

int top;

}Sta;

void print()

{

printf("\n菜單:");

printf("\n1.入棧:");

printf("\n2.出棧:");

printf("\n3.退出:");

}

void printS(Sta S)

{

printf("\n請(qǐng)輸出棧中元素:");

for(int i=S.top;i!=S.base;i--)

printf("%d ",S.value[i-1]);

}

void pushS(Sta S,int e)

{

if(S.top==N)

printf("\n棧滿");

else

S.value[S.top++]=e;

}

void popS(Sta S,int e)

{

if(S.top==S.base)

printf("\n???);

else

{

e=S.value[--S.top];

printf("\n請(qǐng)輸出出棧元素: %d",e);

}

}

void main()

{

Sta S;

int e,choose;

S.base=S.top=0;

do{

print();

printf("\n請(qǐng)輸入你的選項(xiàng):");

scanf("%d",choose);

switch(choose)

{

case 1:

printf("\n請(qǐng)輸入入棧元素:");

scanf("%d",e);

pushS(S,e);

printS(S);

break;

case 2:

popS(S,e);

printS(S);

break;

case 3:

default:

break ;

}

if(choose==3)

break;

}while(1);

}

elem語(yǔ)句輸出的不是元素,而是地址。'>C語(yǔ)言寫(xiě)的一個(gè)堆棧,s->elem語(yǔ)句輸出的不是元素,而是地址。

需要將push函數(shù)略作修改,因?yàn)檫@里傳的是指針s的一個(gè)拷貝,所以對(duì)指針指向的改變不會(huì)影響調(diào)用部分指針的指向,參數(shù)加引用即可。

bool push(stack s,ElementType e)/////////////////引用

{

Node* nodept = (Node *)malloc(sizeof(Node));

if (nodept == NULL)

return false;

else

{

nodept-elem = e;

nodept-next = s;

s = nodept;

}

return true;

}

C語(yǔ)言函數(shù)調(diào)用棧

程序的執(zhí)行過(guò)程可看作連續(xù)的函數(shù)調(diào)用。當(dāng)一個(gè)函數(shù)執(zhí)行完畢時(shí),程序要回到調(diào)用指令的下一條指令(緊接call指令)處繼續(xù)執(zhí)行。函數(shù)調(diào)用過(guò)程通常使用堆棧實(shí)現(xiàn),每個(gè)用戶態(tài)進(jìn)程對(duì)應(yīng)一個(gè)調(diào)用棧結(jié)構(gòu)(call stack)。編譯器使用堆棧傳遞函數(shù)參數(shù)、保存返回地址、臨時(shí)保存寄存器原有值(即函數(shù)調(diào)用的上下文)以備恢復(fù)以及存儲(chǔ)本地局部變量。

不同處理器和編譯器的堆棧布局、函數(shù)調(diào)用方法都可能不同,但堆棧的基本概念是一樣的。

寄存器是處理器加工數(shù)據(jù)或運(yùn)行程序的重要載體,用于存放程序執(zhí)行中用到的數(shù)據(jù)和指令。因此函數(shù)調(diào)用棧的實(shí)現(xiàn)與處理器寄存器組密切相關(guān)。

AX(AH、AL):累加器。有些指令約定以AX(或AL)為源或目的寄存器。輸入/輸出指令必須通過(guò)AX或AL實(shí)現(xiàn),例如:端口地址為43H的內(nèi)容讀入CPU的指令為INAL,43H或INAX,43H。目的操作數(shù)只能是AL/AX,而不能是其他的寄存器。 [5]

BX(BH、BL): 基址寄存器 。BX可用作間接尋址的地址寄存器和 基地址寄存器 ,BH、BL可用作8位通用數(shù)據(jù)寄存器。 [5]

CX(CH、CL):計(jì)數(shù)寄存器。CX在循環(huán)和串操作中充當(dāng)計(jì)數(shù)器,指令執(zhí)行后CX內(nèi)容自動(dòng)修改,因此稱為計(jì)數(shù)寄存器。 [5]

DX(DH、DL):數(shù)據(jù)寄存器。除用作通用寄存器外,在 I/O指令 中可用作端口 地址寄存器 ,乘除指令中用作輔助累加器。 [5]

2.指針和 變址寄存器

BP( Base Pointer Register):基址指針寄存器。 [5]

SP( Stack Pointer Register): 堆棧指針寄存器 。 [5]

SI( Source Index Register):源變址寄存器。 [5]

DI( Destination Index Register):目的變址寄存器。 [5]

函數(shù)調(diào)用棧的典型內(nèi)存布局如下圖所示:

圖中給出主調(diào)函數(shù)(caller)和被調(diào)函數(shù)(callee)的棧幀布局,"m(%ebp)"表示以EBP為基地址、偏移量為m字節(jié)的內(nèi)存空間(中的內(nèi)容)。該圖基于兩個(gè)假設(shè):第一,函數(shù)返回值不是結(jié)構(gòu)體或聯(lián)合體,否則第一個(gè)參數(shù)將位于"12(%ebp)" 處;第二,每個(gè)參數(shù)都是4字節(jié)大小(棧的粒度為4字節(jié))。在本文后續(xù)章節(jié)將就參數(shù)的傳遞和大小問(wèn)題做進(jìn)一步的探討。 此外,函數(shù)可以沒(méi)有參數(shù)和局部變量,故圖中“Argument(參數(shù))”和“Local Variable(局部變量)”不是函數(shù)棧幀結(jié)構(gòu)的必需部分。

其中,主調(diào)函數(shù)將參數(shù)按照調(diào)用約定依次入棧(圖中為從右到左),然后將指令指針EIP入棧以保存主調(diào)函數(shù)的返回地址(下一條待執(zhí)行指令的地址)。進(jìn)入被調(diào)函數(shù)時(shí),被調(diào)函數(shù)將主調(diào)函數(shù)的幀基指針EBP入棧,并將主調(diào)函數(shù)的棧頂指針ESP值賦給被調(diào)函數(shù)的EBP(作為被調(diào)函數(shù)的棧底),接著改變ESP值來(lái)為函數(shù)局部變量預(yù)留空間。此時(shí)被調(diào)函數(shù)幀基指針指向被調(diào)函數(shù)的棧底。以該地址為基準(zhǔn),向上(棧底方向)可獲取主調(diào)函數(shù)的返回地址、參數(shù)值,向下(棧頂方向)能獲取被調(diào)函數(shù)的局部變量值,而該地址處又存放著上一層主調(diào)函數(shù)的幀基指針值。本級(jí)調(diào)用結(jié)束后,將EBP指針值賦給ESP,使ESP再次指向被調(diào)函數(shù)棧底以釋放局部變量;再將已壓棧的主調(diào)函數(shù)幀基指針彈出到EBP,并彈出返回地址到EIP。ESP繼續(xù)上移越過(guò)參數(shù),最終回到函數(shù)調(diào)用前的狀態(tài),即恢復(fù)原來(lái)主調(diào)函數(shù)的棧幀。如此遞歸便形成函數(shù)調(diào)用棧。

EBP指針在當(dāng)前函數(shù)運(yùn)行過(guò)程中(未調(diào)用其他函數(shù)時(shí))保持不變。在函數(shù)調(diào)用前,ESP指針指向棧頂?shù)刂罚彩菞5椎刂?。在函?shù)完成現(xiàn)場(chǎng)保護(hù)之類的初始化工作后,ESP會(huì)始終指向當(dāng)前函數(shù)棧幀的棧頂,此時(shí),若

關(guān)于C語(yǔ)言printf函數(shù)和棧的問(wèn)題

對(duì)于浮點(diǎn)輸出格式來(lái)說(shuō)

%m.nf

其中m是輸出寬度,n是精度,f是格式化控制符

m指定的是輸出數(shù)字字符串的最小長(zhǎng)度,比如你輸出

printf( "%2.3f" , 123.456 ); // 由于實(shí)際輸出的數(shù)字123.456共有7個(gè)字符,大于2個(gè)字符數(shù)量,所以這里的2其實(shí)實(shí)際上沒(méi)起到什么作用,不過(guò)如果你printf( "%8.3f" , 123.456 );,8-7=1,那么結(jié)果將在數(shù)字前面補(bǔ)一個(gè)空格字符,使用printf( "%08.3f" , 123.456 );則是補(bǔ)一個(gè)字符'0'

所以e如果存在于被輸出的數(shù)字串里的話(比如使用%e),它也是要占用m的計(jì)數(shù)的,包括小數(shù)點(diǎn)。

n則是指定輸出精度,也就是小數(shù)點(diǎn)后保留幾位,默認(rèn)不指定.n的時(shí)候printf會(huì)自動(dòng)調(diào)整輸出到默認(rèn)精確位,如果指定了n的話,printf則把數(shù)字保留小數(shù)點(diǎn)后n位輸出。

所以printf( "%f", 123.456 );如果輸出123.456000的話,那么printf( "%.2f", 123.456 );則輸出123.46,


本文標(biāo)題:c語(yǔ)言輸出函數(shù)堆棧,c語(yǔ)言棧的函數(shù)
網(wǎng)頁(yè)URL:http://weahome.cn/article/hdosjh.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部