棧與佇列鏈式儲存結構一貨物上架問題
阿新 • • 發佈:2018-11-09
#include <iostream>
#include<string.h> static int n; //用於輸入貨架(貨架即為棧)的大小 using namespace std; //資訊結構體
typedef struct /*Inform*/ //可以去掉Inform,在需要在結構體中定義結構體物件(指標)時不能去掉
{
string name;
int a;
}Inform; //棧的*順序*結構體
typedef struct Node
{
Inform e;
struct Node *next;
}StackNode,*LinkStack; //佇列*鏈式*結構體
typedef struct QNode
{
Inform e;
struct QNode *next;
}QNode,*QueuePtr; //指向鏈式佇列的頭尾指標
typedef struct
{
QueuePtr fro;
QueuePtr rear;
}LinkQueue; void Found1(LinkStack &s); //貨物上架
void Foundd(LinkQueue &d); //建立順序佇列
void TurnsZ1(LinkStack &s1,LinkQueue d); //對於前天未剩餘(第一天)倒貨
void TurnsZ2(LinkStack &s1,LinkStack s2,LinkStack s3); //對於前天有剩餘倒貨
void Print(LinkStack s1); int main()
{
cout << "請輸入每次上貨的最大值\t";
cin >> n;
LinkStack s1,s2,s3;
s1=s2=s3=NULL; //是否有必要定義建構函式,即建立一個空棧 建立一個佇列,使其頭尾指標指向佇列未存貨物資訊的空結點
LinkQueue d;
cout<<"第一天貨物上架"<<endl;
Found1(s1); //輸入貨物資訊
Foundd(d);
TurnsZ1(s1,d);
Print(s1);
cout<<"第二天貨物上架"<<endl;
if(s1==NULL)
{
Found1(s1);
TurnsZ1(s1,d);
Print(s1);
}
else
{
Found1(s2);
TurnsZ2(s1,s2,s3);
Print(s1);
}
return 0;
} void Found1(LinkStack &s)
{
s=NULL; //定義一個空棧,s連線在p上,即p->next=NULL
Inform i;
i.name="";
cout<<"輸入break表示停止輸入:"<<endl;
while(1)
{
StackNode *p;
p=new StackNode;
cin>>i.name;
if(i.name=="break")
break;
cin>>i.a;
p->e=i;
p->next=s;
s=p;
}
} void Foundd(LinkQueue &q)
{
q.fro=q.rear=new QNode;
q.fro->next=NULL;
q.rear->next=NULL;
} void TurnsZ1(LinkStack &s1,LinkQueue d) //此處隊列表現出來的問題為 d.fro始終與d.rear相等。實際上為對接點的建立(多次使用只建立一次導致一直在修該此指標
//而未儲存下一個結點)還有delete的問題,怎填的結點指標並不能delete,否則該節點將會被刪除
{
Inform i;
//QNode *p=new QNode; 若無下面的,知識在修改佇列第一個元素指向的值,而不是繼續新增
StackNode *s=new StackNode;
while(s1!=NULL)
{
QNode *p=new QNode; //此處十分重要 ,
i=s1->e; //i=s1.e不正確 ,呼叫物件的成員時用“.”,如果是指標或者引用時,利用“->”呼叫其成員
s=s1;
s1=s->next;
delete s;
p->e=i;
p->next=NULL;
d.rear->next=p;
d.rear=p;
//cout<<"rear指向的名字"<<d.rear->e.name<<endl;
//cout<<"fro指向的名字"<<d.fro->next->e.name<<endl; //《問題》此處fro 與 rear 同時移動
}
QNode *p=new QNode;
while(d.fro!=d.rear)
{
StackNode *s=new StackNode;
p=d.fro->next;
i=p->e;
d.fro->next=p->next;
if(p==d.rear)
d.rear=d.fro;
delete p;
s->e=i;
s->next=s1;
s1=s;
}
} void TurnsZ2(LinkStack &s1,LinkStack s2,LinkStack s3)
{
Inform i;
while(s1!=NULL)
{
StackNode *s=new StackNode;
s=s1;
s1=s->next;
s->next=s3;
s3=s;
}
while(s2!=NULL)
{
StackNode *s=new StackNode;
s=s2;
s2=s->next;
s->next=s1;
s1=s;
}
while(s3!=NULL)
{
StackNode *s=new StackNode;
s=s3;
s3=s->next;
s->next=s1;
s1=s;
}
} void Print(LinkStack s1)
{
//StackNode *s=new StackNode;
while(s1!=NULL)
{
cout<<s1->e.name<<" "<<s1->e.a<<endl;
s1=s1->next;
}
} 棧與佇列鏈式儲存結構: 1:掌握棧與佇列的初始化問題,可以通過畫圖進一步理解並記憶其核心內容 a:棧,初始化時申請一個 *S 指向NULL的空地址,存入時,申請空間並與S連線即可(注意棧的尾部結點的next->NULL) b: 佇列:首先建立兩個指標 *pro he *rear 指向同一個空節點,並令其next->NULL,存入時,建立新結點連在rear後面,並且將rear指向新節點,刪除佇列元素時,pro不 動,刪除pro->next即可 2:特別問題: 在存入和刪除元素時,要注意新節點的建立與刪除。 a:建立——存入一個元素需要建立一個新指標,不能建立一個多次對其賦值,這樣不會存入,而是在不斷改變第一個元素的值 b:delete也是如此,在元素存入時,若delete存入的指標,則會使存入的元素空間釋放,即存入進去的內容被刪除
#include<string.h> static int n; //用於輸入貨架(貨架即為棧)的大小 using namespace std; //資訊結構體
typedef struct /*Inform*/ //可以去掉Inform,在需要在結構體中定義結構體物件(指標)時不能去掉
{
string name;
int a;
}Inform; //棧的*順序*結構體
typedef struct Node
{
Inform e;
struct Node *next;
}StackNode,*LinkStack; //佇列*鏈式*結構體
typedef struct QNode
{
Inform e;
struct QNode *next;
}QNode,*QueuePtr; //指向鏈式佇列的頭尾指標
typedef struct
{
QueuePtr fro;
QueuePtr rear;
}LinkQueue; void Found1(LinkStack &s); //貨物上架
void Foundd(LinkQueue &d); //建立順序佇列
void TurnsZ1(LinkStack &s1,LinkQueue d); //對於前天未剩餘(第一天)倒貨
void TurnsZ2(LinkStack &s1,LinkStack s2,LinkStack s3); //對於前天有剩餘倒貨
void Print(LinkStack s1); int main()
{
cout << "請輸入每次上貨的最大值\t";
cin >> n;
LinkStack s1,s2,s3;
s1=s2=s3=NULL; //是否有必要定義建構函式,即建立一個空棧 建立一個佇列,使其頭尾指標指向佇列未存貨物資訊的空結點
LinkQueue d;
cout<<"第一天貨物上架"<<endl;
Found1(s1); //輸入貨物資訊
Foundd(d);
TurnsZ1(s1,d);
Print(s1);
cout<<"第二天貨物上架"<<endl;
if(s1==NULL)
{
Found1(s1);
TurnsZ1(s1,d);
Print(s1);
}
else
{
Found1(s2);
TurnsZ2(s1,s2,s3);
Print(s1);
}
return 0;
} void Found1(LinkStack &s)
{
s=NULL; //定義一個空棧,s連線在p上,即p->next=NULL
Inform i;
i.name="";
cout<<"輸入break表示停止輸入:"<<endl;
while(1)
{
StackNode *p;
p=new StackNode;
cin>>i.name;
if(i.name=="break")
break;
cin>>i.a;
p->e=i;
p->next=s;
s=p;
}
} void Foundd(LinkQueue &q)
{
q.fro=q.rear=new QNode;
q.fro->next=NULL;
q.rear->next=NULL;
} void TurnsZ1(LinkStack &s1,LinkQueue d) //此處隊列表現出來的問題為 d.fro始終與d.rear相等。實際上為對接點的建立(多次使用只建立一次導致一直在修該此指標
//而未儲存下一個結點)還有delete的問題,怎填的結點指標並不能delete,否則該節點將會被刪除
{
Inform i;
//QNode *p=new QNode; 若無下面的,知識在修改佇列第一個元素指向的值,而不是繼續新增
StackNode *s=new StackNode;
while(s1!=NULL)
{
QNode *p=new QNode; //此處十分重要
i=s1->e; //i=s1.e不正確 ,呼叫物件的成員時用“.”,如果是指標或者引用時,利用“->”呼叫其成員
s=s1;
s1=s->next;
delete s;
p->e=i;
p->next=NULL;
d.rear->next=p;
d.rear=p;
//cout<<"rear指向的名字"<<d.rear->e.name<<endl;
//cout<<"fro指向的名字"<<d.fro->next->e.name<<endl; //《問題》此處fro 與 rear 同時移動
}
QNode *p=new QNode;
while(d.fro!=d.rear)
{
StackNode *s=new StackNode;
p=d.fro->next;
i=p->e;
d.fro->next=p->next;
if(p==d.rear)
d.rear=d.fro;
delete p;
s->e=i;
s->next=s1;
s1=s;
}
} void TurnsZ2(LinkStack &s1,LinkStack s2,LinkStack s3)
{
Inform i;
while(s1!=NULL)
{
StackNode *s=new StackNode;
s=s1;
s1=s->next;
s->next=s3;
s3=s;
}
while(s2!=NULL)
{
StackNode *s=new StackNode;
s=s2;
s2=s->next;
s->next=s1;
s1=s;
}
while(s3!=NULL)
{
StackNode *s=new StackNode;
s=s3;
s3=s->next;
s->next=s1;
s1=s;
}
} void Print(LinkStack s1)
{
//StackNode *s=new StackNode;
while(s1!=NULL)
{
cout<<s1->e.name<<" "<<s1->e.a<<endl;
s1=s1->next;
}
} 棧與佇列鏈式儲存結構: 1:掌握棧與佇列的初始化問題,可以通過畫圖進一步理解並記憶其核心內容 a:棧,初始化時申請一個 *S 指向NULL的空地址,存入時,申請空間並與S連線即可(注意棧的尾部結點的next->NULL) b: 佇列:首先建立兩個指標 *pro he *rear 指向同一個空節點,並令其next->NULL,存入時,建立新結點連在rear後面,並且將rear指向新節點,刪除佇列元素時,pro不 動,刪除pro->next即可 2:特別問題: 在存入和刪除元素時,要注意新節點的建立與刪除。 a:建立——存入一個元素需要建立一個新指標,不能建立一個多次對其賦值,這樣不會存入,而是在不斷改變第一個元素的值 b:delete也是如此,在元素存入時,若delete存入的指標,則會使存入的元素空間釋放,即存入進去的內容被刪除