程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> ZOJ2425

ZOJ2425

編輯:C++入門知識


題意很簡單,就是給出n,m求n個數下逆序個數為m的最小排列,求出最小排列。
我用的暴力+貪心的方法。  用m與當前個數(也就是剩下需要寫出的個數)的最大逆序個數進行比較,容易知道當前逆序最大的個數為s=(n)*(n-1)/2;
如果s==m直接逆序打印沒用過的數。如果m<s,那麼繼續用m與s1=(n-1)(n-2)/2,(n-1個最大逆序個數比較),然後找出沒用過的(m-s1+1)個數,即為當前要打印的個數,
如果 m>=s,直接找一個最小沒用過的數打印。

一開始沒用long long還有各種細節不注意錯了好幾次,代碼寫得也很爛,網上好像有其他更簡單的方法。

下面是AC代碼:
[cpp] 
#include<iostream> 
#include<cstdio> 
using namespace std; 
int mark[50005]; 
 
int main(){ 
 
    int i,j; 
 
    long long n,m,t; 
 
    while(cin>>n>>m){ 
      // printf("%I64d\n",m); 
        if(n==-1&&m==-1) 
            break; 
        long long s=n*(n-1)/2; 
    //  cout<<s<<endl; 
    //  printf("%I64d\n",s); 
    //  return 0; 
        int flag=1; 
        t=n; 
        for(i=1;i<=n;i++) 
            mark[i]=0; 
 
        if(m==0){ 
            cout<<1; 
            for(i=2;i<=n;i++) 
                cout<<" "<<i; 
            cout<<endl; 
 
        } 
        else{ 
 
 
            while(m){ 
                if(m==s){ 
                    for(i=n;i>=1;i--){ 
 
                        if(mark[i]==0){ 
                            if(flag){ 
                                flag=0; 
                                cout<<i; 
                                mark[i]=1; 
 
                            } 
                            else{ 
                                cout<<" "<<i; 
                                mark[i]=1; 
                            } 
                        } 
                    } 
                    break; 
 
                } 
                else if(m<s){ 
                    long long nexts=(t-1)*(t-2)/2; 
                    if(m>nexts){ 
                        long long key=m-nexts; 
                        int count=0,k; 
 
                        for(i=1;i<=n;i++){ 
                            if(count==key+1) break; 
                            if(mark[i]==0){ 
                                count++; 
                                k=i; 
                            } 
                        } 
                        if(flag){ 
                            cout<<k; 
                            flag=0; 
 
                        } 
                        else{ 
                            cout<<" "<<k; 
                        } 
                        mark[k]=1; 
 
                        m=nexts; 
                    } 
                    else{ 
                        for(i=1;i<=n;i++) 
                            if(mark[i]==0){ 
                                if(flag){ 
                                    flag=0; 
                                    cout<<i; 
                                    mark[i]=1; 
                                    break; 
                                } 
                                else{ 
                                    cout<<" "<<i; 
                                    mark[i]=1; 
                                    break; 
                                } 
                            } 
 
                    } 
                } 
                t--; 
                s=t*(t-1)/2; 
            } 
            cout<<endl; 
        } 
    } 
 
 
 
    return 0; 

 

 

作者:w00w12l

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved