201903-5 317号子任务(100分优化过程)

csp 201903-5 317号子任务

这个只是用来记录含辛茹苦的优化过程,具体讲解在这里:
201903-5 317号子任务(100分)

测试用例:
7 6 2
1 0 1 0 1 1 0
1 4 1
1 2 3
2 4 4
2 3 5
2 5 7
6 7 5

30分 弗洛伊德:

#include <iostream>
#include <iostream>
#include <vector>
#include <algorithm>
#include <queue>

#define INF 0x7fffffff

using namespace std;


int main()
{

    int n,m,k;

    while(cin>>n>>m>>k){
        vector<bool> important;

        for(int i = 0; i < n; i++){
            int temp;
            cin>> temp;
            if(temp == 1){
                important.push_back(true);
            }else{
                important.push_back(false);
            }
        }

        int* eage = new int[n*n];
        //init
         for(int i = 0; i < n; i++){
            for(int j = 0; j < n; j++){
                if(i == j){
                    eage[i*n+j] = 0;
                }else{
                    eage[i*n+j] = INF;
                }
            }
        }
        for(int j = 0; j < m; j++){
            int left;
            int right;
            int weight;
            cin>>left>>right>>weight;

            if(weight< eage[(left-1)*n+right-1]){
                eage[(left-1)*n+right-1] = weight;
                eage[(right-1)*n+left-1] = weight;
            }
        }


        //int* dp = new int[n*n];
        //cal
        for(int p = 0; p < n;p++){
            for(int i = 0; i < n; i++){
                for(int j = 0; j < i; j++){
                    if(eage[i*n+p] != INF && eage[p*n+j] != INF){
                        eage[i*n+j] = min(eage[i*n+p]+eage[p*n+j],eage[i*n+j]);
                        eage[j*n+i] = eage[i*n+j];
                    }
                }
            }
        }
		


        for(int i = 0; i < n;i++){

            int count = 0;
            priority_queue<int,vector<int>,less<int> > myqueue;
            for(int j = 0; j < n;j++){
                if(important[j]){
                    int weight = eage[i*n+j];
                    if(count >= k){
                        if(weight < myqueue.top()){
                            myqueue.pop();
                            myqueue.push(weight);
                        }
                    }else{
                        if(weight != INF){
                            myqueue.push(weight);
                            count++;
                        }
                    }
                }
            }
            int size  = myqueue.size();
            int sum = 0;
            for(int p = 0; p <size && p < k; p++){
                sum += myqueue.top();
                myqueue.pop();
            }
            cout << sum<<endl;
        }
        delete [] eage;
    }


    return 0;
}

30分 迪杰斯特拉:

#include <iostream>
#include <iostream>
#include <vector>
#include <algorithm>
#include <queue>

#define INF 0x7fffffff

using namespace std;


int main()
{

    int n,m,k;

    while(cin>>n>>m>>k){
        vector<bool> important;

        for(int i = 0; i < n; i++){
            int temp;
            cin>> temp;
            if(temp == 1){
                important.push_back(true);
            }else{
                important.push_back(false);
            }
        }

        int* eage = new int[n*n];
        //init
        for(int i = 0; i < n; i++){
            for(int j = 0; j < n; j++){
                if(i == j){
                    eage[i*n+j] = 0;
                }else{
                    eage[i*n+j] = INF;
                }
            }
        }
        for(int j = 0; j < m; j++){
            int left;
            int right;
            int weight;
            cin>>left>>right>>weight;

            if(weight< eage[(left-1)*n+right-1]){
                eage[(left-1)*n+right-1] = weight;
                eage[(right-1)*n+left-1] = weight;
            }
        }


        int* mindis = new int[n*n];
        //cal
        for(int i = 0; i < n; i++){
            for(int j = 0; j < n; j++){
                mindis[i*n+j] = eage[i*n+j];
            }
        }
        for(int i = 0; i< n; i++){
        	//int* currdis = new int[n];
        	vector<int> currdis;
        	vector<bool> visit;
        	for(int j = 0; j < n; j++){
        		//currdis[j] = dis[i*n+j];
        		currdis.push_back(eage[i*n+j]);
        		visit.push_back(false);
			}
			
			int min = INF;
			int postion = -1;
			while(true){
				//min one
				for(int j = 0; j < n; j++){
	        		if(!visit[j] && currdis[j] < min){
	        			min = currdis[j];
	        			postion = j;
					}
				}
				
				if(min == INF){
					break;
				}
				
				//visit
				visit[postion] = true;
				mindis[i*n+postion] = min;
				mindis[postion*n+i] =  mindis[i*n+postion];
				
				//update
				for(int j = 0; j < n; j++){
	        		if(!visit[j]){
	        			if(eage[postion*n+j] != INF && min+eage[postion*n+j] < currdis[j]){
	        				currdis[j] = min+eage[postion*n+j];
						}
					}
				}
				
				min = INF;	
			}
		}


        for(int i = 0; i < n;i++){

            int count = 0;
            priority_queue<int,vector<int>,less<int> > myqueue;
            for(int j = 0; j < n;j++){
                if(important[j]){
                    int weight = mindis[i*n+j];
                    if(count >= k){
                        if(weight < myqueue.top()){
                            myqueue.pop();
                            myqueue.push(weight);
                        }
                    }else{
                        if(weight != INF){
                            myqueue.push(weight);
                            count++;
                        }
                    }
                }
            }
            int size  = myqueue.size();
            int sum = 0;
            for(int p = 0; p <size && p < k; p++){
                sum += myqueue.top();
                myqueue.pop();
            }
            cout << sum<<endl;
        }

		delete [] mindis;
        delete [] eage;
    }


    return 0;
}

只用了行星发动点,依旧是30分呜呜呜

#include <iostream>
#include <iostream>
#include <vector>
#include <algorithm>
#include <queue>

#define INF 0x7fffffff

using namespace std;


int main()
{

    int n,m,k;

    while(cin>>n>>m>>k){
        vector<bool> important;

        for(int i = 0; i < n; i++){
            int temp;
            cin>> temp;
            if(temp == 1){
                important.push_back(true);
            }else{
                important.push_back(false);
            }
        }

        int* eage = new int[n*n];
        //init
        for(int i = 0; i < n; i++){
            for(int j = 0; j < n; j++){
                if(i == j){
                    eage[i*n+j] = 0;
                }else{
                    eage[i*n+j] = INF;
                }
            }
        }
        for(int j = 0; j < m; j++){
            int left;
            int right;
            int weight;
            cin>>left>>right>>weight;

            if(weight< eage[(left-1)*n+right-1]){
                eage[(left-1)*n+right-1] = weight;
                eage[(right-1)*n+left-1] = weight;
            }
        }


        int* mindis = new int[n*n];
        //cal
        for(int i = 0; i < n; i++){
            for(int j = 0; j < n; j++){
                mindis[i*n+j] = eage[i*n+j];
            }
        }
        for(int i = 0; i< n; i++){

            if(!important[i]){
                continue;
            }

        	vector<int> currdis;
        	vector<bool> visit;

        	for(int j = 0; j < n; j++){
        		currdis.push_back(eage[i*n+j]);
        		visit.push_back(false);
			}

			int min = INF;
			int postion = -1;
			while(true){
				//min one
				for(int j = 0; j < n; j++){
	        		if(!visit[j] && currdis[j] < min){
	        			min = currdis[j];
	        			postion = j;
					}
				}

				if(min == INF){
					break;
				}

				//visit
				visit[postion] = true;
				mindis[i*n+postion] = min;
				mindis[postion*n+i] =  mindis[i*n+postion];


				//update
				for(int j = 0; j < n; j++){
	        		if(!visit[j]){
	        			if(eage[postion*n+j] != INF && min+eage[postion*n+j] < currdis[j]){
	        				currdis[j] = min+eage[postion*n+j];
						}
					}
				}

				min = INF;
			}


		}

        for(int i = 0; i < n;i++){

                int count = 0;
                priority_queue<int,vector<int>,less<int> > myqueue;
                for(int j = 0; j < n;j++){
                    if(important[j]){
                        int weight = mindis[i*n+j];
                        if(count >= k){
                            if(weight < myqueue.top()){
                                myqueue.pop();
                                myqueue.push(weight);
                            }
                        }else{
                            if(weight != INF){
                                myqueue.push(weight);
                                count++;
                            }
                        }
                    }
                }
                int size  = myqueue.size();
                int sum = 0;
                for(int p = 0; p <size && p < k; p++){
                    sum += myqueue.top();
                    myqueue.pop();
                }
                cout << sum<<endl;
        }

		delete [] mindis;
        delete [] eage;
    }


    return 0;
}

我继续改,用了heap的迪杰斯特拉,30分

#include <iostream>
#include <vector>
#include <algorithm>
#include <queue>

#define INF 0x7fffffff

using namespace std;

struct node{
    int id;
    int dis;
};


struct cmp{
    bool operator()(const node& a,const node& b){
        return a.dis > b.dis;
    }
};

int main()
{

    int n,m,k;

    while(cin>>n>>m>>k){
        vector<int> important;

        for(int i = 0; i < n; i++){
            int temp;
            cin>> temp;
            if(temp == 1){
                important.push_back(i);
            }
        }

        int* eage = new int[n*n];
        //init
        for(int i = 0; i < n; i++){
            for(int j = 0; j < n; j++){
                if(i == j){
                    eage[i*n+j] = 0;
                }else{
                    eage[i*n+j] = INF;
                }
            }
        }
        for(int j = 0; j < m; j++){
            int left;
            int right;
            int weight;
            cin>>left>>right>>weight;

            if(weight< eage[(left-1)*n+right-1]){
                eage[(left-1)*n+right-1] = weight;
                eage[(right-1)*n+left-1] = weight;
            }
        }


        int* mindis = new int[n*n];
        //cal
        for(int w = 0; w< important.size(); w++){

            int i = important[w];


        	//vector<int> currdis;
        	priority_queue<node,vector<node>,cmp> heap;
        	vector<bool> visit;

        	for(int j = 0; j < n; j++){
        		//currdis.push_back(eage[i*n+j]);
        		node tempnode;
                tempnode.id = j;
                tempnode.dis = eage[i*n+j];
                heap.push(tempnode);
        		visit.push_back(false);
			}



			while(!heap.empty()){
				//min one
                node minnode = heap.top();
                heap.pop();

                int postion = minnode.id;
                int min = minnode.dis;

                if(visit[postion]){
                    continue;
                }


				//visit
				visit[postion] = true;
				mindis[i*n+postion] = min;
				mindis[postion*n+i] =  mindis[i*n+postion];


				if(min == INF){
					continue;
				}


				//update
				for(int j = 0; j < n; j++){
	        		if(!visit[j] && eage[postion*n+j] != INF){
	        			node tempnode;
	        			tempnode.id = j;
	        			tempnode.dis = min+eage[postion*n+j];
	        			heap.push(tempnode);
					}
				}

			}


		}

        for(int i = 0; i < n;i++){

                int count = 0;
                priority_queue<int,vector<int>,less<int> > myqueue;

                for(int w = 0; w < important.size();w++){
                    int j = important[w];
                    int weight = mindis[i*n+j];
                    if(count >= k){
                        if(weight < myqueue.top()){
                            myqueue.pop();
                            myqueue.push(weight);
                        }
                    }else{
                        if(weight != INF){
                            myqueue.push(weight);
                            count++;
                        }
                    }
                }
                int size  = myqueue.size();
                int sum = 0;
                for(int p = 0; p <size && p < k; p++){
                    sum += myqueue.top();
                    myqueue.pop();
                }
                cout << sum<<endl;
        }

		delete [] mindis;
        delete [] eage;
    }


    return 0;
}

啊啊啊啊100分!!!!!

#include <iostream>
#include <vector>
#include <algorithm>
#include <queue>

#define INF 0x7fffffff

using namespace std;

struct node{
    int id;
    int dis;
};


struct cmp{
    bool operator()(const node& a,const node& b){
        return a.dis > b.dis;
    }
};

int main()
{

    int n,m,k;

    while(scanf("%d %d %d",&n,&m,&k)!= EOF){
        vector<int> important;

        for(int i = 0; i < n; i++){
            int temp;
            //cin>> temp;
            scanf("%d",&temp);
            if(temp == 1){
                important.push_back(i);
            }
        }

        //int* eage = new int[n*n];
        vector<vector<node> > eage(n);

        //init
        for(int i = 0; i < n; i++){

            node temp;
            temp.id = i;
            temp.dis = 0;
            eage[i].push_back(temp);
        }
        for(int j = 0; j < m; j++){
            int left;
            int right;
            int weight;
            //cin>>left>>right>>weight;
            scanf("%d %d %d",&left,&right,&weight);
//            if(weight< eage[(left-1)*n+right-1]){
//                eage[(left-1)*n+right-1] = weight;
//                eage[(right-1)*n+left-1] = weight;
//            }
            node temp;
            temp.id = right-1;
            temp.dis = weight;
            eage[left-1].push_back(temp);

            temp.id = left-1;
            eage[right-1].push_back(temp);
        }


        int* mindis = new int[n*n];
        //cal
        for(int w = 0; w< important.size(); w++){

            int i = important[w];



        	//vector<int> currdis;
        	priority_queue<node,vector<node>,cmp> heap;
        	vector<bool> visit;

        	for(int j = 0; j < n; j++){
        		visit.push_back(false);
			}

            for(int j = 0; j < eage[i].size(); j++){
                heap.push(eage[i][j]);
			}




			while(!heap.empty()){
				//min one
                node minnode = heap.top();
                heap.pop();

                int postion = minnode.id;
                int min = minnode.dis;


                if(visit[postion]){
                    continue;
                }

                //printf("from: %d;min: %d;position: %d\n",i,min,postion);

				//visit
				visit[postion] = true;
				mindis[i*n+postion] = min;
				mindis[postion*n+i] =  mindis[i*n+postion];


				//update
				for(int j = 0; j < eage[postion].size(); j++){
	        		if(!visit[eage[postion][j].id]){
	        			node tempnode;
	        			tempnode.id = eage[postion][j].id;
	        			tempnode.dis = min+eage[postion][j].dis;
	        			heap.push(tempnode);
					}
				}

			}

            for(int j = 0; j < n; j++){
                if(!visit[j]){
                    mindis[i*n+j] = INF;
                    mindis[j*n+i] =  mindis[i*n+j];
                }
			}


		}

        for(int i = 0; i < n;i++){

                int count = 0;
                priority_queue<int,vector<int>,less<int> > myqueue;

                for(int w = 0; w < important.size();w++){
                    int j = important[w];
                    int weight = mindis[i*n+j];
                    if(count >= k){
                        if(weight < myqueue.top()){
                            myqueue.pop();
                            myqueue.push(weight);
                        }
                    }else{
                        if(weight != INF){
                            myqueue.push(weight);
                            count++;
                        }
                    }
                }
                int size  = myqueue.size();
                int sum = 0;
                for(int p = 0; p <size && p < k; p++){
                    sum += myqueue.top();
                    myqueue.pop();
                }
                //cout << sum<<endl;
                printf("%d\n",sum);
        }

		delete [] mindis;
    }


    return 0;
}

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值