Combinaciones posibles. Recursividad C#

Muchas veces para resolver algunos problemas, necesitamos saber cuantas formas posibles hay de escribir un número, una palabra. A través de los algoritmos de combinaciones podemos resolver muchos problemas, que no podemos hacer facilmente con una calculadora, o con la mente. Por ejemplo, de cuantas formas posibles se puede descomponer un número en sumandos? De cuantas formas posibles podemos combinar ciertas letras? Este tipo de problemas son los que trataremos en este post.

Primero veremos y comentaremos el algoritmo que nos permite saber cuantas combinaciones posibles se pueden hacer con ciertas letras.

Veamos el código:

public static void Combina(string s)
{
        //Iniciamos este array auxiliar para
        //marcar los caracteres que ya combinamos
	bool []marcas = new bool[s.Length];
        //Llamamos al método recursivo
	Combina(s, "", marcas);
}
 
static void Combina(string original, string combinado, bool[]marcas)
{
        //Imprimimos la combinación si ya cambiamos
        //todas las letras una vez
	if(original.Length == combinado.Length)
		Console.WriteLine(combinado);
 
	for(int i = 0; i < marcas.Length; i++)
	{
           //Vemos si está marcada para no volverla a combinar
	   if(!marcas[i])
	   {
                //Marcamos el caracter que vamos a combinar
		marcas[i] = true;
                //Invocamos al metodo recursivo añadiendo
                //un caracter al string que combinamos
		Combina(original, combinado + original[i], marcas);
                //Desmarcamos el caracter para poder usarlo
                //en otras combinaciones
		marcas[i] = false;
	   }
	}
}

Como ven es un algoritmo muy sencillo, y no tan largo, donde usamos la técnica de backtracking, o vuelta atrás, que vimos hace un tiempo en este post. Espero les halla servido de ayuda este problemita, con esto podrá por ejemplo, saber de cuantas formas posibles se pueden combinar las letras a, n y c.

Si hacemos algo así:

Combina("abc");
Console.ReadLine();

esto es lo que devolvería el programa:

abc
acb
bac
bca
cab
cba

Ya se encargarán ustedes de buscarle las aplicaciones que lleva, también pueden tratar de hacer este algoritmo un poco más eficientes, piensen un poco en el como…

En el proximo post, veremos entonces todas las permutaciones que podemos hacer para descomponer un número en sumandos.

dudas=> comentarios

Compártelo:
  • Meneame
  • Digg
  • del.icio.us
  • Facebook
  • BarraPunto
  • Google Bookmarks
  • Reddit
  • StumbleUpon
  • Technorati
  • TwitThis
  • Wikio
  • LinkedIn
  • Netvibes
  • Bitacoras.com
Entradas relacionadas:
  • Tres formas de Invertir un String
  • 3 Comentarios
    1. jOefaYNo Gravatar | 28 Octubre 2009 a las 12:59

      Exelente amigo, lo cale y corre bastante bien :D

      solo algo, en la parte de lo de adentro del for se me hizo algo extraña y me marco error:

      for(int i = 0; i < marcas.Length; i++)

      lo que hice fue cambiarle un poco para que dejara de marcar el error dejandola asi y corrio bien.

      for(int i = 0; i < marcas.Length; i++)

    2. fulanoNo Gravatar | 23 Noviembre 2009 a las 16:37

      Muy chulo tu codigo.. pero – a juzgar por el ejemplo – eso son PERMUTACIONES y no COMBINACIONES

    3. TomyNo Gravatar | 25 Noviembre 2009 a las 3:45

      JOefaY:
      Si, parece que el interprete que uso, tenía algún error e interpretó el signo ‘<‘ como ‘<’.

      fulano:
      Tienes razón, el metodo devuelve todas las permutaciones, pero puse combinaciones para no tener que explicar entonces, que cosa son las variaciones sin repetición, con repetición, combianciones, permutaciones, etc.

    Escribe un comentario