我有一个给定的单词,因为我需要在相应的排序单词上找到它的排列数。 假设我有单词BABA,其相应的排序单词是,AABB,如果我开始置换这个排序的单词,将作为第二个“单词”来到AABB,不管字母重复,然后是ABAB,ABBA,BABA ..所以这个变换单词BABA的数字是5。 简单的方法是开始做所有可能的组合,然后与初始单词进行比较。 到目前为止,我已经完成了..
import java.util.Arrays;
public class Permutation {
int location =1;
public static char[] warray;
void printArray(char []a) {
for (int i = 0; i < a.length; i++) {
System.out.print(a[i]+" ");
}
System.out.println("location " + location );
}
void permute(char []a,int k ) {
if(k==a.length) {
location++;
// Check if the permuted word is the one looking for.
if (Arrays.equals(a, warray))
{ System.out.println("final iteration k" + k);
printArray(a);
System.exit(0);}
}
else
for (int i = k; i < a.length; i++) {
char temp=a[k];
a[k]=a[i];
a[i]=temp;
permute(a,k+1);
}
}
public static void main(String[] args) {
if (args[0].length() > 25 ) {
System.out.println(" Word not in permited range " );
System.exit(0);
}
else {
Permutation p=new Permutation();
warray = new char[args[0].length()];
char [] wpermute = new char[args[0].length()];
for (int i = 0; i < args[0].length(); i++) {
warray[i] = new Character(args[0].charAt(i));
wpermute[i] = new Character(args[0].charAt(i));
}
Arrays.sort(wpermute);
System.out.print("sorted word : " );
for (int i = 0; i < wpermute.length; i++) {
System.out.print(wpermute[i]);
}
p.permute(wpermute,0);
}
}
但这可能是非常缓慢的表现。 我的第二个猜测是,从二进制搜索开始,首字母是未排序的单词,计算可能的排列,将这个字母作为排列的第一个字母,然后是第二个字母......所以...听起来不错吗?
答案 0 :(得分:2)
如果您只有2个字母,并且该字词的长度为N
且A的数字为n
,那么排列的数量为N choose n
。
如果您总共有N
个字母,n_a
,n_b
,...,n_z
描述了每个字母的数量,那么排列的总数是
N!/(n_a! n_b! n_c! ... n_z!)
查看Multinomials,向下滚动到排列位。
答案 1 :(得分:0)
另一个词是QUESTION,它的排序单词是EINOQSTU。 对于问题,q在位置1,在新单词的位置5中,需要做多少排列在位置1 = 20161。 现在我接受第二个问题,是U,在排序单词的第8位,需要做多少排列,是24481
我想,我可以计算,而不是执行将字母放在y位置所需的数字排列,处于X位置。然后,所有的总和,将是该单词所需的排列。
现在,如何计算这些数字,我知道必须使用阶乘加其他东西..不是吗?
答案 2 :(得分:0)
所以我最终完成了代码,是的,需要检查多项式。 也从这里的相关帖子中获得了部分想法。 但这是我的代码。
package WordPuzzle;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
/** Rafael G. */
public class WordPuzzle {
static String sortWord (String[] wordinput){
char [] wsorted = new char[wordinput[0].length()];
wsorted = wordinput[0].toCharArray();
Arrays.sort(wsorted);
String aux="";
for (int i = 0; i < wsorted.length; i++) {
aux = aux + wsorted[i];
}
return aux;
}
static void calculatePerm(String wordtofind,String wordsorted)
{
int sum = 0;
int numberpermutations;
char nextchar;
int charlocremainder =0;
String lowerLetters;
String greaterLetters;
Map<Character, Integer> characterCounts = new HashMap<Character, Integer> ();
int count ;
char letter;
int factorial;
int [] factorials = new int [wordsorted.length()+1];
factorial =1;
numberpermutations = 1;
int nMinusI;
int nextcharcount;
// set a mapping of repeated letters and its number
// and store factorial calculation.
for (int i = 0; i < wordsorted.length(); i++) {
letter = wordsorted.charAt(i);
factorial = factorial * (i+1);
factorials[i+1]= factorial;
count = characterCounts.containsKey(letter) ? characterCounts.get(letter) + 1 : 1;
characterCounts.put(letter, count);
}
String trimWord = new String(wordsorted);
for (int i = 0; i < wordtofind.length() ; i++){
nMinusI = wordtofind.length()-(i+1);
nextchar = wordtofind.charAt(i);
charlocremainder = trimWord.indexOf(nextchar);
lowerLetters = trimWord.substring(0, charlocremainder);
// Calculate the denominator which is the number of repeated letters
// of the formula (N-i)! * (Na+Nb) /Na!Nb!..
nextcharcount = characterCounts.get(nextchar);
characterCounts.put(nextchar, nextcharcount-1);
int denomfact = factorials[nextcharcount];
if (lowerLetters.length() > 1){
char x = lowerLetters.charAt(0);
char y = x;
for (int k = 1 ; k < lowerLetters.length(); k++){
y = lowerLetters.charAt(k);
if (x != y) {
denomfact = denomfact * factorials[characterCounts.get(x)];
x = y;
}
}
denomfact = denomfact * factorials[characterCounts.get(y)];
}
numberpermutations = factorials[nMinusI] * lowerLetters.length() / denomfact;
sum = sum + numberpermutations;
greaterLetters= trimWord.substring(charlocremainder+1);
trimWord = lowerLetters.concat(greaterLetters);
}
System.out.println(" Rank of permutation " + (sum+1));
}
/**
* @param args the command line arguments
*/
public static void main(String[] args) {
long startTime = System.nanoTime();
String wordsorted;
String wordentered;
if (args[0].length() > 25 ) {
System.out.println("Word not in permited range " );
System.exit(0);
}
else {
wordentered = args[0].toUpperCase();
wordsorted = sortWord(args).toUpperCase();
calculatePerm(wordentered,wordsorted);
}
long endTime = System.nanoTime();
System.out.println("Took "+(endTime - startTime)/1000000000.0 + " seconds");
System.out.println("Took "+(endTime - startTime)* 0.000001 + " milliseconds");
}
}