經典題:求字典序第m個的序列(2062)
Subset sequence
Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 4587 Accepted Submission(s): 2228
Problem Description Consider the aggregate An= { 1, 2, …, n }. For example, A1={1}, A3={1,2,3}. A subset sequence is defined as a array of a non-empty subset. Sort all the subset sequece of An in lexicography order. Your task is to find the m-th one.
Input The input contains several test cases. Each test case consists of two numbers n and m ( 0< n<= 20, 0< m<= the total number of the subset sequence of An ).
Output For each test case, you should output the m-th subset sequence of An in one line.
Sample Input 1 1 2 1 2 2 2 3 2 4 3 10
Sample Output 1 1 1 2 2 2 1 2 3 1
設f[i]為1到n的排成的序列的總數,則可由打表發現:f[i]=n*(f[i-1]+1),這裡其實蘊含著遞迴的思想。我們想要知道序列的具體位置,由規律性:zushu=ceil(m*1.0/(f[n-1]+1)),然後就可以取出首位元素了,剩下的序列可由遞迴求解,同時,原序列需要更新,元素被取出。然後就要更新內層的組數了:m=m-(zushu-1)*(f[n-1]+1)-1,因為每個序列的最小的那一個就一個元素,其後沒有元素,所以需要-1。n還需自減一次。
/*------------------Header Files------------------*/ #include <iostream> #include <cstring> #include <string> #include <cstdio> #include <algorithm> #include <cstdlib> #include <ctype.h> #include <cmath> #include <stack> #include <queue> #include <deque> #include <map> #include <vector> #include <limits.h> using namespace std; /*------------------Definitions-------------------*/ #define LL long long #define PI acos(-1.0) #define INF 0x3F3F3F3F #define MOD 10E9+7 #define MAX 500050 /*---------------------Work-----------------------*/ void work() { int n; LL m,f[25]; f[0]=0; for(int i=1;i<=20;i++) f[i]=i*(f[i-1]+1); while(scanf("%d%I64d",&n,&m)==2) { int num[25]; for(int i=1;i<=n;i++) num[i]=i; bool flag=true; while(m>0) { int zushu=ceil(m*1.0/(f[n-1]+1)); //計算所屬組數 if(!flag) printf(" "); flag=false; printf("%d",num[zushu]); for(int i=zushu;i<n;i++) //合併掉這個位置 num[i]=num[i+1]; m=m-(zushu-1)*(f[n-1]+1)-1; //-1是因為第一個只有一個數字 n--; } printf("\n"); } } /*------------------Main Function------------------*/ int main() { //freopen("test.txt","r",stdin); //freopen("cowtour.out","w",stdout); //freopen("cowtour.in","r",stdin); work(); return 0; }
相關推薦
經典題:求字典序第m個的序列(2062)
Subset sequence Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 4587 Accepte
求單向連結串列倒序第m個元素
原題為某遊戲公司試題,大意如下:對於一個單向連結串列,試寫出找到它的倒序第m個元素(m >= 1)的函式,注意變數命名、註釋、時間複雜度、空間複雜度。注:要求寫出可編譯並可以執行通過的程式程式碼。 這道題的常規做法或者說首先想到直覺的方法M1是先求得連結串列的長度,即元素總個數n,然
SUBLEX Lexicographical Substring Search 求字典序第k小的子串
題目:求字串字典序第k小的子串 思路:統計每個狀態的子串的個數,按字典序尋找 程式碼: #pragma comment(linker, "/STACK:1024000000,1024000000") #include<iostream> #include<
SPOJ Lexicographical Substring Search 求字典序第k大子串 後綴自動機
scan span ogr set mes cin () spa bit 題目傳送門 思路:按字典序,小的字符優先選取。對於一個字符,如果以這個字符開頭的子串大於等於k個,那說明這個字符是應該選的,並且選完之後,可能還要繼續選。如果以這個字符開頭的子串小於k個,說明這個字
MOOC北京理工《C語言程式設計(上)》第5周第3題:求最小m值
題目內容: 求滿足下列不等式的最小 m。 1 + 2 + 3 + 4 + ...... + m ≥ n 例如:n=100,當 m =14 時,滿足:1+2+3+4+...+13=91<100,而 1+2+3+4+......+14=105>100
給定整數n和m, 將1到n的這n個整數按字典序排列之後, 求其中的第m個數。
自己構造了一個map,自定義了map的比較函式,程式碼通過率為50%,不知道為什麼這樣的複雜度還不能通過?程式碼如下#include <iostream> #include <vector> #include <map> #include
第四題:求A+B
題目,求A+B,每一行將包含兩個整數A和B程序到檔案結束。對於每種情況,在一行中輸出A+B。 題解:輸入A.B,再建立迴圈,直到不再輸入時停止,輸出A+B #include <iostream> using namespace std; int main() { int a
第九題:求眾數
問題描述 給定一個大小為 n 的陣列,找到其中的眾數。眾數是指在陣列中出現次數大於 ⌊ n/2 ⌋ 的元素。 你可以假設陣列是非空的,並且給定的陣列總是存在眾數。 示例 1: 輸入: [3,2,3] 輸出: 3 示例 2: 輸入: [2,2,1,1,1,2,2] 輸出:
LeetCode——第題:求二叉樹深度
題目: 給定一個二叉樹,找出其最大深度。 二叉樹的深度為根節點到最遠葉子節點的最長路徑上的節點數。 說明: 葉子節點是指沒有子節點的節點。 示例: 給定二叉樹 [3,9,20,null,n
【雙向bfs(一次可也)】【非簡單圖的最短路】UVa1599 Ideal Path 【紫書6-20經典例題】【無向圖求字典序最小的最短路】
【雙向bfs(一次也可)】【非簡單圖的最短路】UVa1599 Ideal Path 【紫書6-20經典例題】【無向圖求字典序最小的最短路】 New labyrinth attraction is open in New Lostland amusement p
演算法題:求N!末尾0的個數和求二進位制數中1的個數
1、給定一個整數,那麼N的階乘N!末尾有多少個0呢? 解題思路:N!=K*10^M,M的值即為N!末尾0的個數。又10^M=(2^M)*(5^M),因為一個數進行質因數分解後,2出現的概率比5大得多。所以只有計算出1到N包含多少個5的因子 public class demo2 {
一道簡單的演算法題:不借助第三變數來交換兩個變數的值
今天做筆試碰到一道簡單的演算法題:不借助第三變數來交換兩個變數的值,記錄一下。 交換兩個變數的值的普遍做法都是藉助第三變數,這樣具有較高的可讀性。 a = 3 b = 5 t = a a = b b = t 但是,如果記憶體有限,只允許用2個變數呢? 強大的CS當然有辦法解決
演算法與設計經典題:大整數乘法(教材2-4)
給定兩個整數u和v,他們分別有m和n為數字,且m≤n,用通常的乘法求uv的值需要O(mn)時間,可以將u和v均看作是有n位數字的大整數,用本章介紹的分治法,在O(n^(log3))時間內計算uv的值,當m<<n時,此法效率不高。設計演算法在O(nlog2/3)時間計算uv的值 在O(
BZOJ3994:約數個數和(莫比烏斯反演:求[1,N]*[1,M]的矩陣的因子個數)
Description 設d(x)為x的約數個數,給定N、M,求 Input 輸入檔案包含多組測試資料。 第一行,一個整數T,表示測試資料的組數。 接下來的T行,每行兩個整數N、M。 Ou
給兩個字串(都是大寫字母,且長的相等) 求字典序在這兩個字串之間的一個等長字串
題目有點坑,要仔細想想(水題一道) #include<iostream> #include<cstring> #include<algorithm> using namespace std; int main() { string a,b,
C語言——求素數和——第n個素數到第m個素數之間所有的素數的和,包括第n個素數和第m個素數
程式的邏輯性很關鍵,首先想好分幾步走,每一步定義什麼,輸出什麼結果 OK想好了,開始吧 #include<stdio.h> int main() {//1.0初始化結果變數n,m int n,m,result=0; scanf("%d %d",&n,&m)
模擬題 P1030 求先序排列 洛谷 簡單
題目描述 給出一棵二叉樹的中序與後序排列。求出它的先序排列。(約定樹結點用不同的大寫字母表示,長度 \le 8≤8)。 輸入輸出格式 輸入格式: 22行,均為大寫字母組成的字串,表示一棵二叉樹的中序與後序排列。 輸出格式: 11行,表示一棵二叉樹的先序。 輸入輸出樣例 輸入樣例#
Java求第M個與第N個素數之間的素數和
題目內容: 我們認為2是第一個素數,3是第二個素數,5是第三個素數,依次類推。 現在,給定兩個整數n和m,0<n<=m<=200,你的程式要計算第n個素數到第m個素數之間所有的素數的和,包括第n個素數和第m個素數。 注意,是第n個素數到第m個素
三道習題(1、將單詞表中由相同字母組成的單詞歸成一類,每類單詞按照單詞的首字母排序,並按 #每類中第一個單詞字典序由大到小排列輸出各個類別。 #輸入格式:按字典序由小到大輸入若干個單詞,每個單詞佔一行,以end結束輸入。)
#coding=gbk ''' 1、將單詞表中由相同字母組成的單詞歸成一類,每類單詞按照單詞的首字母排序,並按 #每類中第一個單詞字典序由大到小排列輸出各個類別。 #輸入格式:按字典序由小到大輸入若干個單詞,每個單詞佔一行,以end結束輸入。 #cinema #iceman #maps #spam #a
給兩個字串(都是大寫字母,且長的相等) 求字典序在這兩個字串之間的一個等長字串
題目有點坑,要仔細想想(水題一道) #include<iostream> #include<cstring> #include<algorithm> using namespace std; int main() { strin