数据结构与算法A实验一顺序表
7 - 1 两个有序链表序列的合并
答案:
#include<bits/stdc++.h>
using namespace std;
struct node{ // 定义节点结构体
int data; // 值
node *next; // 指向下一个节点的索引
};
node *build(node *head){ // 建立链表
head=new node;
node *tail,*p;
head->next=NULL;
tail=head;
int k;
while(cin>>k&&k!=-1){ // 输入链表的值
p=new node;
p->data=k;
p->next=tail->next;
tail->next=p;
tail=p;
}
return head;
}
node *Merge(node *h1,node *h2){ // 合并链表
node *t1=h1->next,*t2=h2->next;
node *p,*tail;
node *head=new node;
head->next=NULL;
tail=head;
while(t1&&t2){
if(t1->data<t2->data){ // 如果t1值小合并到head中
p=new node;
p->data=t1->data;
p->next=tail->next;
tail->next=p;
tail=p;
t1=t1->next;
}else{ // 如果t2值小合并到head中
p=new node;
p->data=t2->data;
p->next=tail->next;
tail->next=p;
tail=p;
t2=t2->next;
}
}
if(t1) tail->next=t1; // 如果h1链表有剩余 把剩余的放入
if(t2) tail->next=t2; // 如果h2链表有剩余 把剩余的放入
return head;
}
void show(node *head){ // 输出列表
node *p=head->next;
while(p){ // 节点不为空
if(p->next) cout<<p->data<<" "; // 最后一个节点输出换行
else cout<<p->data<<endl; // 不是最后一个节点输出空格
p=p->next; // 指针移动到下一个节点
}
}
void solve(){
node *head1=new node; // 定义链表一
node *head2=new node; // 定义链表二
head1=build(head1); // 建立链表一
head2=build(head2); // 建立链表二
//show(head1);
//show(head2);
node *head=Merge(head1,head2); // 合并链表一、二
if(head->next) show(head); // 如果链表不为空 输出链表head
else cout<<"NULL"<<endl; // 如果链表为空 输出 NULL
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 2 顺序表的建立及遍历
答案:
#include<bits/stdc++.h>
using namespace std;
struct node{ // 定义节点结构体
int data; // 值
node *next; // 指向下一个节点的索引
};
node *build(node *head,int n){ // 建立链表
head=new node;
node *tail,*p;
head->next=NULL;
tail=head;
for(int i=1;i<=n;i++){ // 输入链表的值
p=new node;
cin>>p->data;
p->next=tail->next;
tail->next=p;
tail=p;
}
return head;
}
void show(node *head){ // 输出列表
node *p=head->next;
while(p){ // 节点不为空
if(p->next) cout<<p->data<<" "; // 最后一个节点输出换行
else cout<<p->data<<endl; // 不是最后一个节点输出空格
p=p->next; // 指针移动到下一个节点
}
}
void solve(){
int n;
cin>>n;
node *head=new node; // 定义链表
head=build(head,n); // 建立链表
show(head); // 输出链表head
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 3 顺序表(删除)
#include<bits/stdc++.h>
using namespace std;
struct node{ // 定义节点结构体
int data; // 值
node *next; // 指向下一个节点的索引
};
node *build(node *head,int n){ // 建立链表
head=new node;
node *tail,*p;
head->next=NULL;
tail=head;
for(int i=1;i<=n;i++){ // 输入链表的值
p=new node;
cin>>p->data;
p->next=tail->next;
tail->next=p;
tail=p;
}
return head;
}
node *del(node *head,int l,int r){ // 删除节点
node *q=head->next;
node *p=head;
while(q){ // 若q没有到最后一个节点
if(q->data>=l&&q->data<=r){ // 如果满足删除条件
p->next=q->next;
free(q);
q=p->next;
}else{ // 如果不满足删除条件, p、q节点都向后挪动
p=p->next;
q=q->next;
}
}
return head;
}
void show(node *head){ // 输出列表
node *p=head->next;
while(p){ // 节点不为空
if(p->next) cout<<p->data<<" "; // 最后一个节点输出换行
else cout<<p->data<<endl; // 不是最后一个节点输出空格
p=p->next; // 指针移动到下一个节点
}
}
void solve(){
int n;
cin>>n;
node *head=new node; // 定义链表
head=build(head,n); // 建立链表
int l,r;
cin>>l>>r;
head=del(head,l,r);
show(head); // 输出链表head
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 4 最大子列和问题
答案:
DP方法:
#include<bits/stdc++.h>
#define ll long long
const int N = 1e5 + 10;
using namespace std;
ll n;
ll a[N];
ll maxn=-1;
inline void solve(){
cin>>n;
for(ll i=1;i<=n;i++) cin>>a[i];
ll sum=0;
ll res=-1;
for(ll i=1;i<=n;i++){
sum+=a[i];
if(sum<0) sum=0;
res=max(res,sum);
}
cout<<res<<endl;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
int t=1;
//cin>>t;
while(t--) solve();
return 0;
}
分治算法:
#include<bits/stdc++.h>
#define ll long long
const int N = 2e5 + 10;
using namespace std;
int n;
int a[N];
int maxn=0;
//int tot=0;
int get(int l,int r){ // 递归求字段和
//tot++;
if(l==r){ // 递归终止条件
if(a[l]<0) return 0;
return a[l];
}
int maxn=0;
int mid=l+r-1>>1; // 取中点
int sum=0;
int maxl=get(l,mid); // 递归左边
int maxr=get(mid+1,r); // 递归左边
int ml=0,mr=0;
for(int i=mid+1;i<=r;i++){ // 从中点到右边依次求和求最大值
sum+=a[i];
mr=max(mr,sum);
}
sum=0;
for(int i=mid;i>=l;i--){ // 从中点到左边依次求和求最大值
sum+=a[i];
ml=max(ml,sum);
}
maxn=max(max(maxl,maxr),ml+mr); // 取左边、右边和全部长度的最大值
if(maxn<0) maxn=0;
return maxn;
}
inline void solve(){
cin>>n;
for(int i=1;i<=n;i++) cin>>a[i];
cout<<get(1,n)<<endl;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
int t=1;
while(t--) solve();
return 0;
}
7 - 5 递增有序顺序表的插入
#include<bits/stdc++.h>
using namespace std;
struct node{ // 定义节点结构体
int data; // 值
node *next; // 指向下一个节点的索引
};
node *build(node *head,int n){ // 建立链表
head=new node;
node *tail,*p;
head->next=NULL;
tail=head;
for(int i=1;i<=n;i++){ // 输入链表的值
p=new node;
cin>>p->data;
p->next=tail->next;
tail->next=p;
tail=p;
}
return head;
}
void show(node *head){ // 输出列表
node *p=head->next;
while(p){ // 节点不为空
cout<<p->data<<","; // 输出节点
p=p->next; // 指针移动到下一个节点
}
}
node *Insert(node *head,int x){
node *q=head->next;
node *p=head;
bool tag=0;
while(q&&!tag){
if(q->data<x){ // 如果当前节点值小于x 继续往下走
q=q->next;
p=p->next;
}else{ // 如果当前值大于x 则插入x
tag=1;
node *t=new node;
t->data=x;
p->next=t;
t->next=q;
p=t;
}
}
if(!tag){ // 如果x大于原链表所有元素则插入到最后
node *t=new node;
t->data=x;
p->next=t;
t->next=NULL;
}
return head;
}
void solve(){
int n;
cin>>n;
node *head=new node; // 定义链表
head=build(head,n); // 建立链表
int x;
cin>>x;
head=Insert(head,x);
show(head); // 输出链表head
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 6 数组元素逆置
答案
#include<bits/stdc++.h>
const int N = 1e5 + 10;
using namespace std;
int a[N];
void solve(){
for(int i=1;i<=10;i++) cin>>a[i];
for(int i=1;i<=10;i++){
if(i==10) cout<<a[i]<<endl;
else cout<<a[i]<<",";
}
for(int i=10;i>=1;i--){
if(i==1) cout<<a[i]<<endl;
else cout<<a[i]<<",";
}
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 7 一元多项式的加法
#include<bits/stdc++.h>
#define ll long long
#define eb emplace_back
#define x first
#define y second
const int N = 1e7 + 10;
using namespace std;
map<ll,ll>ind;
vector<ll>res;
void solve(){
int n;
cin>>n;
int a,b;
for(int i=1;i<=n;i++){ // 输入第一个表达式
cin>>a>>b;
ind[b]+=a; // 对应指数位置加上系数值
}
cin>>n;
for(int i=1;i<=n;i++){
cin>>a>>b;
ind[b]+=a;
}
for(auto i:ind){ // 遍历指数 去除系数为零的指数
if(i.y){
res.eb(i.x);
res.eb(i.y);
}
}
if(res.size()){ // 如果不是零多项式 倒序输出
for(int i=res.size()-1;i>=0;i--){
if(i!=res.size()-1) cout<<" ";
cout<<res[i];
}
cout<<endl;
}else cout<<"0 0"<<endl; // 如果是零多项式 输出 0 0
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 8 数组元素的删除
#include<bits/stdc++.h>
#define ll long long
#define eb emplace_back
#define x first
#define y second
const int N = 1e7 + 10;
using namespace std;
int a[N];
void solve(){
int n;
cin>>n;
for(int i=1;i<=n;i++) cin>>a[i]; // 输入原数组
int q;
cin>>q;
while(q--){ // 输入删除位置
int k;
cin>>k;
n--; // 缩减总数
for(int i=k;i<=n;i++){ // 数组移位 = 删除元素
a[i]=a[i+1];
}
}
for(int i=1;i<=n;i++){
if(i==n) cout<<a[i]<<endl;
else cout<<a[i]<<" ";
}
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}
7 - 9 数列循环右移
#include<bits/stdc++.h>
#define ll long long
#define eb emplace_back
#define x first
#define y second
const int N = 1e7 + 10;
using namespace std;
int a[N];
void solve(){
int n,m;
cin>>n>>m;
m%=n; // 除去循环的次数,把多次变成移动一个循环
for(int i=1;i<=n;i++) cin>>a[i]; // 输入原数组
if(!m){
for(int i=1;i<=n;i++) cout<<a[i]<<" ";
}
else{
for(int i=n-m+1;i<=n;i++) cout<<a[i]<<" "; // 输出移位到前面的
for(int i=1;i<=n-m;i++) cout<<a[i]<<" "; // 输出移位到后面的
}
}
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
solve();
return 0;
}