After small changes this program was submitted successfully.
The main bug was that you used lexicografical comparison in next function instead
of alphabetic one (function lessthan).
Also, youd better care about possible spaces in the input, nobody said that word starts
from the line beginning.
IMHO, its better to use standard STL functions for such simple tasks
You could have written 3 times shorter program just calling
sort(v.begin(), v.end(), lessthan)
and
next_permutation(v.begin(), v.end(), lessthan)
Haha yes I wrote the lessthan function but only used it in the initial sorting and not in the next() function itself. The fact that it gave me correct output for sample data discouraged me from checking my code. Thank you so much for your detailed response and suggestions.
You algoritm is correct, but if you carefully read the problem statement, you will discover that the ordering is
AaBbCc..........Zz and not ABC....abc.
/*---------------------------------------------------*/
/* Compara dois caracteres retornando: */
/* 0 Se o caracter 1 e igual a 2 */
/* -1 Se o caracter 1 e menor que o 2 */
/* 1 Se o caracter 1 e maior que o 2 */
/*---------------------------------------------------*/
int CompararChar(char cChar1, char cChar2)
{
char cTemp1 = tolower(cChar1);
char cTemp2 = tolower(cChar2);
if(cTemp1 < cTemp2)
return -1;
else if(cTemp1 > cTemp2)
return 1;
else
{
if (islower(cChar1))
{
/* Se os caracteres 1 e 2 sao lowercase eles sao iguais */
if (islower(cChar2))
return 0;
/* Se o caracter 1 e lowercase e o 2 e uppercase */
/* 1 e maior que 2 */
else
return 1;
}
else
{
/* Se os caracteres 1 e 2 sao uppercase eles sao iguais */
if (isupper(cChar2))
return 0;
/* Se o caracter 1 e uppercase e o 2 e lowercase */
/* 1 e menor que 2 */
else
return -1;
}
}
}
/*---------------------------------------------------*/
/* Compara duas strings retornando: */
/* 0 Se a string 1 e igual a 2 */
/* -1 Se a string 1 e menor que a 2 */
/* 1 Se a string 1 e maior que a 2 */
/*---------------------------------------------------*/
int Comparar(char *pcString1, char *pcString2)
{
int iComp;
/* Obtem o tamanho das strings a serem comparadas */
int iLen1 = strlen(pcString1);
int iLen2 = strlen(pcString2);
/*Compara os caracteres correntes das duas string */
iComp = CompararChar(*pcString1, *pcString2);
/* Caso o os carateres correntes sejam diferentes, */
/* retornar indicando se a string 1 e maior ou menor */
/* que a string 2*/
if (iComp)
return iComp;
}
/* Se as strings tem o mesmo tamanho elas sao iguais */
if (iLen1 == iLen2)
return 0;
/* Se a string 1 e menor que a 2 */
else if (iLen1 < iLen2)
return -1;
/* Se a string 1 e maior que a 2 */
else
return 1;
}
void QuickSort(char ppVetor[MAX_ARRAY][MAX_LEN], int iIni, int iFim)
{
int iEsq, iDir;
char *pItem;
char pTemp[MAX_LEN];
if( iFim > iIni ) /* i.e. at least 2 elements, then */
{
iEsq = iIni;
iDir = iFim;
pItem = ppVetor[iIni]; /* NB. just an estimate! */
void Sort(char ppVetor[MAX_ARRAY][MAX_LEN], int iLen)
{
if (iLen <= 0) return;
QuickSort(ppVetor, 0, iLen - 1);
}
/*---------------------------------------------------*/
/* Compara duas strings retornando: */
/* 0 Se a string 1 e igual a 2 */
/* -1 Se a string 1 e menor que a 2 */
/* 1 Se a string 1 e maior que a 2 */
/*---------------------------------------------------*/
long GerarPermutacao(char palavra[MAX_LEN], int i, int n, char lista[MAX_ARRAY][MAX_LEN])
{
int j = 0, s=0, x=0;
char temp;
if (i == n-1)
{
strcpy(lista[cont],palavra);
Sort(lista, cont);
cont++;
}
else
{
for(j=i; j<n; j++)
{
temp = palavra;
palavra = palavra[j];
palavra[j] = temp;
x = GerarPermutacao(palavra,i+1,n, lista);
Shamin,
I did some changes in my code but now I got a "Runtime Error (SIGSEGV)" message. I think that the problem is because the length of the word used by judge is >9.
For a length word = 10 I need a vector length of 3628800, but if try to declare this vector I have a "Runtime Error (SIGSEGV)" before I try to execute the code.
Could you help me?
/*---------------------------------------------------*/
/* Compara dois caracteres retornando: */
/* 0 Se o caracter 1 e igual a 2 */
/* -1 Se o caracter 1 e menor que o 2 */
/* 1 Se o caracter 1 e maior que o 2 */
/*---------------------------------------------------*/
int CompararChar(char cChar1, char cChar2)
{
char cTemp1 = tolower(cChar1);
char cTemp2 = tolower(cChar2);
if(cTemp1 < cTemp2)
return -1;
else if(cTemp1 > cTemp2)
return 1;
else
{
if (islower(cChar1))
{
/* Se os caracteres 1 e 2 sao lowercase eles sao iguais */
if (islower(cChar2))
return 0;
/* Se o caracter 1 e lowercase e o 2 e uppercase */
/* 1 e maior que 2 */
else
return 1;
}
else
{
/* Se os caracteres 1 e 2 sao uppercase eles sao iguais */
if (isupper(cChar2))
return 0;
/* Se o caracter 1 e uppercase e o 2 e lowercase */
/* 1 e menor que 2 */
else
return -1;
}
}
}
/*---------------------------------------------------*/
/* Compara duas strings retornando: */
/* 0 Se a string 1 e igual a 2 */
/* -1 Se a string 1 e menor que a 2 */
/* 1 Se a string 1 e maior que a 2 */
/*---------------------------------------------------*/
int Comparar(char *pcString1, char *pcString2)
{
int iComp;
/* Obtem o tamanho das strings a serem comparadas */
int iLen1 = strlen(pcString1);
int iLen2 = strlen(pcString2);
/*Compara os caracteres correntes das duas string */
iComp = CompararChar(*pcString1, *pcString2);
/* Caso o os carateres correntes sejam diferentes, */
/* retornar indicando se a string 1 e maior ou menor */
/* que a string 2*/
if (iComp)
return iComp;
}
/* Se as strings tem o mesmo tamanho elas sao iguais */
if (iLen1 == iLen2)
return 0;
/* Se a string 1 e menor que a 2 */
else if (iLen1 < iLen2)
return -1;
/* Se a string 1 e maior que a 2 */
else
return 1;
}
void DownHeap(char ppVetor[MAX_ARRAY][MAX_LEN], long lIni, long lFim)
/* PRE: a[k+1..N] is a heap */
/* POST: a[k..N] is a heap */
{
long lFilho;
char pItem[MAX_LEN];
strcpy(pItem, ppVetor[lIni]);
while (lIni <= lFim/2) /* k has child(s) */
{
lFilho = 2*lIni;
void Sort(char ppVetor[MAX_ARRAY][MAX_LEN], int iLen)
{
if (iLen <= 0) return;
HeapSort(ppVetor, iLen - 1);
}
/*---------------------------------------------------*/
/* Compara duas strings retornando: */
/* 0 Se a string 1 e igual a 2 */
/* -1 Se a string 1 e menor que a 2 */
/* 1 Se a string 1 e maior que a 2 */
/*---------------------------------------------------*/
long GerarPermutacao(char palavra[MAX_LEN], int i, int n, char lista[MAX_ARRAY][MAX_LEN])
{
int j = 0, s=0, x=0;
char temp;
if (i == n-1)
{
strcpy(lista[cont],palavra);
cont++;
}
else
{
for(j=i; j<n; j++)
{
temp = palavra;
palavra = palavra[j];
palavra[j] = temp;
x = GerarPermutacao(palavra,i+1,n, lista);
I don't really understand your code since most of it is not in English.. :p But here's what I think:
1) Character comparison is too slow. Simply compare by ASCII values is a lot faster.
2) Don't treat strings as arrays, treat them as pointers, so increment pointers instead of incrementing indices. that's a lot faster too.
3) I believe you are generating all possible permutations, store them, then sort them, then print them. This is wasteful.. a simple hint: You do not need to store them if you organise that starting data.
/*---------------------------------------------------*/
/* Compara dois caracteres retornando: */
/* 0 Se o caracter 1 e igual a 2 */
/* -1 Se o caracter 1 e menor que o 2 */
/* 1 Se o caracter 1 e maior que o 2 */
/*---------------------------------------------------*/
int CompararChar(char cChar1, char cChar2)
{
char cTemp1 = tolower(cChar1);
char cTemp2 = tolower(cChar2);
if(cTemp1 < cTemp2)
return -1;
else if(cTemp1 > cTemp2)
return 1;
else
{
if (islower(cChar1))
{
/* Se os caracteres 1 e 2 sao lowercase eles sao iguais */
if (islower(cChar2))
return 0;
/* Se o caracter 1 e lowercase e o 2 e uppercase */
/* 1 e maior que 2 */
else
return 1;
}
else
{
/* Se os caracteres 1 e 2 sao uppercase eles sao iguais */
if (isupper(cChar2))
return 0;
/* Se o caracter 1 e uppercase e o 2 e lowercase */
/* 1 e menor que 2 */
else
return -1;
}
}
}
/*---------------------------------------------------*/
/* Compara duas strings retornando: */
/* 0 Se a string 1 e igual a 2 */
/* -1 Se a string 1 e menor que a 2 */
/* 1 Se a string 1 e maior que a 2 */
/*---------------------------------------------------*/
int Comparar(char *pcString1, char *pcString2)
{
int iComp;
/* Obtem o tamanho das strings a serem comparadas */
int iLen1 = strlen(pcString1);
int iLen2 = strlen(pcString2);
/*Compara os caracteres correntes das duas string */
iComp = CompararChar(*pcString1, *pcString2);
/* Caso o os carateres correntes sejam diferentes, */
/* retornar indicando se a string 1 e maior ou menor */
/* que a string 2*/
if (iComp)
return iComp;
}
/* Se as strings tem o mesmo tamanho elas sao iguais */
if (iLen1 == iLen2)
return 0;
/* Se a string 1 e menor que a 2 */
else if (iLen1 < iLen2)
return -1;
/* Se a string 1 e maior que a 2 */
else
return 1;
}
void DownHeap(char ppVetor[MAX_ARRAY][MAX_LEN], long lIni, long lFim)
/* PRE: a[k+1..N] is a heap */
/* POST: a[k..N] is a heap */
{
long lFilho;
char pItem[MAX_LEN];
strcpy(pItem, ppVetor[lIni]);
while (lIni <= lFim/2) /* k has child(s) */
{
lFilho = 2*lIni;
void Sort(char ppVetor[MAX_ARRAY][MAX_LEN], int iLen)
{
if (iLen <= 0) return;
HeapSort(ppVetor, iLen - 1);
}
/*---------------------------------------------------*/
/* Compara duas strings retornando: */
/* 0 Se a string 1 e igual a 2 */
/* -1 Se a string 1 e menor que a 2 */
/* 1 Se a string 1 e maior que a 2 */
/*---------------------------------------------------*/
long GerarPermutacao(char palavra[MAX_LEN], int i, int n, char lista[MAX_ARRAY][MAX_LEN])
{
int j = 0, s=0, x=0;
char temp;
if (i == n-1)
{
strcpy(lista[cont],palavra);
cont++;
}
else
{
for(j=i; j<n; j++)
{
temp = palavra;
palavra = palavra[j];
palavra[j] = temp;
x = GerarPermutacao(palavra,i+1,n, lista);
I am using Disjkastra's algorithm to generate the permutations of the given string in lexicographical ( dictonary ) order. But it is taking a lot of time when the string length exceeds 8.
Can u guys help me in speeding up my program.
[c]
#include <stdio.h>
#include <string.h>
int main(void)
{
unsigned n;
char str[20],tstr[21];
unsigned register x,i,j,r,s,len;
tstr ^= tstr[j] ^= tstr ^= tstr[j];
looks cool
but
t = tstr
tstr = tstr[j]
tstr = t
is faster usually
but that's not the point. The point is that given the string, you should be able to generate immediately without computation.. in other words, your algorithm is wrong.