• Publicidad

Organizar información de ortólogos

Perl aplicado a la bioinformática

Re: Organizar información de ortólogos

Notapor igarrom » 2014-02-03 16:13 @717

Disculpa, explorer. Como bien dices, esas líneas no deberían estar dispuestas de esa forma puesto que esos identificadores no están relacionados entre sí. Es un error.
igarrom
Perlero nuevo
Perlero nuevo
 
Mensajes: 11
Registrado: 2014-01-28 04:06 @212

Publicidad

Re: Organizar información de ortólogos

Notapor explorer » 2014-02-06 08:18 @387

Aunque creo que ya sé cuál debe ser la salida correcta, deberías intentar reeditar el mensaje anterior, y quitar las líneas duplicadas o incorrectas.

Mientras, estoy dando vueltas al problema... es muy interesante...
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Organizar información de ortólogos

Notapor igarrom » 2014-02-06 10:11 @466

De acuerdo,

Estos son los ficheros de entrada id:
Sintáxis: [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
A       B               C               D
Gene_1  103485499       550923130       489128835
Gene_2  103485500       550923131       489128838
Gene_3  103485501       550923133       489128842
Gene_4  103485502       550923134       489128844
Gene_5  103485503       550923135       489128847
Gene_6  103485504       550923136       489128849
Gene_7  103485505       550923137       489128852
Gene_8  103485506       550923138       489128854
Gene_9  103485507       550923139       489128857
Gene_10 103485508       550923140       489128860
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Y estos los ficheros de entrada comp:
Sintáxis: [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
B               A
103485500       Gene_1
103485501       Gene_5
103485502       Gene_8
103485503       Gene_2

C               A
550923135       Gene_10
550923136       Gene_1
550923137       Gene_8

C               B
550923138       103485504
550923139       103485508

D               A
489128852       Gene_4
489128854       Gene_10
489128857       Gene_8
489128860       Gene_3

D               B
489128838       103485507
489128842       103485506
489128844       103485503

D               C
489128849       550923140
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

El resultado esperado sería el siguiente:
Sintáxis: [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
A         B          C           D
Gene_1    103485500
Gene_1                550923136
Gene_2    103485503
Gene_3                           489128860
Gene_4                           489128852
Gene_5    103485501
Gene_6
Gene_7
Gene_8    103485502
Gene_8               550923137
Gene_8                           489128857
Gene_9
Gene_10                          489128854
Gene_10              550923135
          103485499
          103485503              489128844
          103485504  550923138
          103485505
          103485506              489128842
          103485507              489128838
          103485508  550923139
                     550923130
                     550923131
                     550923133
                     550923134
                     550923140    489128849
                                  489128835
                                  489128847
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Aunque en este ejemplo no existen grupos de 3 o 4 ortólogos (solo aparecen parejas entre 2 organismos), en mi fichero real hay casos de ese tipo, en el que A tiene ortólogo con B y C y a su vez B y C lo son entre sí. Tanto en los ficheros .comp como en el fichero de salida, las parejas de ortólogos tendrán que estar separadas por un tabulador.

Muchas gracias,

Inma
igarrom
Perlero nuevo
Perlero nuevo
 
Mensajes: 11
Registrado: 2014-01-28 04:06 @212

Re: Organizar información de ortólogos

Notapor igarrom » 2014-02-20 04:36 @234

Hola, Perleros,

¿Alguna idea sobre cómo realizar el programa? Una cosa que no he mencionado y que quizás facilite las cosas es que los ficheros de entrada no tienen que estar obligatoriamente organizados como he mencionado (aunque en principio a mi es la mejor organización que se me ha ocurrido). Con esto quiero decir que si proponéis una diferente forma de ir añadiendo la información al programa será bienvenida.

Sigo probando cosas (sobre todo usando "hashes"), pero nada... no consigo el resultado que quiero, me resulta un problema muy complejo y necesito organizar los datos como dije.

Saludos y muchas gracias de antemano.

Inma
igarrom
Perlero nuevo
Perlero nuevo
 
Mensajes: 11
Registrado: 2014-01-28 04:06 @212

Re: Organizar información de ortólogos

Notapor explorer » 2014-02-20 12:39 @569

Es que el asunto sí que es complejo: se trata de una operación de conjuntos de elementos.

Si A está relacionado con B, y B está relacionado con C, entonces solo podemos escribir los tres genes en la misma línea de salida, si A está también relacionado con C.

Si no, tendremos que sacar dos líneas de salida, correspondientes a las dos relaciones. Y el tema se complica si tenemos que mirar cuatro archivos (o generalizar para N archivos).

Le estoy dando vueltas desde hace días, pero ahora estoy ocupado con algo gordo. Cuando tenga un rato, lo vuelvo a mirar. Mientras, a ver si alguien más se anima a resolverlo.
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Organizar información de ortólogos

Notapor explorer » 2014-03-20 17:37 @775

Una pregunta:

Si A está relacionado con B, B está relacionado con C, y C está relacionado con D, ¿es necesario que también estén relacionados A con C y A con D y B con D?

Preguntado de otra manera: los ortólogos forman una estrella de relaciones (todos con todos), o solo es necesaria una relación en anillo?
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Organizar información de ortólogos

Notapor igarrom » 2014-03-24 04:30 @229

Hola, explorer.

En la mayoría de los casos si A está relacionado con B, B está relacionado con C, y C está relacionado con D, A estará relacionado con C y con D y B con D. Pero cabe la posibilidad de que no sea así.

Hemos considerado ortólogas dos proteínas cuando en el "Reciprocal Best-Hits BLAST" o blast cruzado, el alineamiento ha tenido una identidad mayor del 30% y un porcentaje de cobertura de las proteínas (de ambas) mayor del 70 %. Por este motivo, si A está relacionado con B porque entre ambas la identidad es del 31 % y la cobertura del 71 % y B está relacionada con C porque entre ambas la identidad es del 31 % y la cobertura del 71 %, puede ocurrir que entre A y C también haya una cobertura del 71 % pero la identidad sea del 29 %, en cuyo caso no se considerarán ortólogos.

Sé que puede ser un poco enrevesada la explicación, espero que se entienda.

Millones de gracias por la ayuda.
igarrom
Perlero nuevo
Perlero nuevo
 
Mensajes: 11
Registrado: 2014-01-28 04:06 @212

Re: Organizar información de ortólogos

Notapor explorer » 2014-04-01 07:23 @349

Sí, sí que entiendo eso, lo del porcentaje de coincidencia.

El tema es cómo encontrar relaciones entre los genes.

A ver... otra pregunta...

Cuando estamos hablando de relaciones de genes entre A y B, a lo que nos referimos es a 'un' solo gen de A, ¿no? En más detalle:

si A está relacionado con B, y
si B está relacionado con C

entonces, son ortólogos si A está relacionado con C, pero además, el gen de A es el mismo con el que se relacionaba con B. ¿Es así? ¿O vale cualquier gen de A?

Y lo mismo con cuatro: A, B, C, D. Para que sean ortólogos, deben existir 6 relaciones (A<=>B, A<=>C, A<=>D, B<=>C, B<=>D y C<=>D), siendo A uno solo y el mismo gen en todas las relaciones en las que aparece la letra A. ¿Es así?
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Organizar información de ortólogos

Notapor igarrom » 2014-04-01 07:49 @367

Correcto, explorer, es exactamente como lo has descrito.
igarrom
Perlero nuevo
Perlero nuevo
 
Mensajes: 11
Registrado: 2014-01-28 04:06 @212

Re: Organizar información de ortólogos

Notapor explorer » 2014-04-05 23:25 @018

Esta es una posible solución.

He modificado los archivos de entrada, para que existan dos conjuntos de tres ortólogos, y uno de cuatro.

Los archivos A, B, C, y D .id son los mismos que antes. Lo que cambian son los archivos de relaciones:
Sintáxis: (B_vs_A.comp) [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
103485500       Gene_1
103485501       Gene_5
103485502       Gene_8
103485503       Gene_2
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Sintáxis: (C_vs_A.comp) [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
550923136       Gene_1
550923137       Gene_8
550923135       Gene_10
550923131       Gene_1
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Sintáxis: (C_vs_B.comp) [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
550923138       103485504
550923139       103485508
550923131       103485500
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Sintáxis: (D_vs_A.comp) [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
489128860       Gene_3
489128852       Gene_4
489128857       Gene_8
489128847       Gene_8
489128854       Gene_10
489128838       Gene_1
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Sintáxis: (D_vs_B.comp) [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
489128844       103485503
489128842       103485506
489128838       103485507
489128857       103485508
489128838       103485500
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Sintáxis: (D_vs_C.comp) [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
489128849       550923140
489128847       550923137
489128857       550923139
489128838       550923131
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Entonces, con el siguiente programa,
Sintáxis: (ortologos.pl) [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. #!/usr/bin/perl
  2. #
  3. # Ortólogos
  4. #
  5. # Joaquín Ferrero, 20140406
  6. #
  7. # Dada una serie de archivos que contienen una relación de genes de organismos,
  8. # y otra serie de archivos que indican los ortólogos entre los genes de distintos
  9. # organismos, obtener una tabla con el resumen de ortólogos entre todos los organismos.
  10. #
  11. use v5.14;
  12. use autodie;
  13.  
  14. use File::Basename;
  15. use File::Slurp;
  16.  
  17. ### Constantes
  18. my $DIR = './ortologos';
  19.  
  20.  
  21. ### Leer archivos con datos ####################################################
  22. my @nombres_archivos = glob("$DIR/*.id");
  23.  
  24. my @organismos;                                                 # nombres de los organismos
  25. my %genes_de_organismo;                                         # genes por cada organismo
  26.  
  27. for my $archivo (@nombres_archivos) {
  28.     my $organismo = basename($archivo, '.id');
  29.  
  30.     push @organismos, $organismo;                               # el nombre es a partir del archivo
  31.  
  32.     my @genes = read_file($archivo, chomp => 1);                # leemos sus genes
  33.  
  34.     $genes_de_organismo{$organismo} = [ @genes ];               # y los guardamos
  35. }
  36.  
  37. @organismos = sort @organismos;                                 # ordenación alfabética
  38.  
  39. # traductor, de nombre de organismo a número de columna dentro de la tabla
  40. my %organismo_a_columna = map { $organismos[$_] => $_ } 0 .. $#organismos;
  41.  
  42.  
  43. ### Leer archivos de relaciones ################################################
  44. my %ortologos;
  45.  
  46. for my $archivo (glob("$DIR/*.comp")) {                         # para todos los archivos
  47.     my($org1, $org2) = $archivo =~ /(\w+)_vs_(\w+)/;            # organismos que se relacionan
  48.  
  49.     my @relaciones = read_file($archivo, chomp => 1);           # leemos relaciones
  50.  
  51.     for (@relaciones) {
  52.         my($gen1, $gen2) = split;                               # los dos genes que intervienen
  53.  
  54.         ## La estructura a crear es la de un hash de arrays
  55.         ##
  56.         ## %ortologos{ ortologo } => [ ortologo [, ortologo, ...] ]
  57.         ##
  58.         ## Por cada ortólogo, guardamos un array anónimo con el resto de ortólogos
  59.         ## con los que se relaciona.
  60.         ##
  61.         ## Los ortólogos tienen la forma: "$organismo;$gen"
  62.         ##
  63.         push @{$ortologos{"$org1;$gen1"}}, "$org2;$gen2";       # creamos dos relaciones:
  64.         push @{$ortologos{"$org2;$gen2"}}, "$org1;$gen1";       # (relación conmutativa)
  65.     }
  66.  
  67. }
  68.  
  69. ### Análisis ###################################################################
  70. my %visto;                                                      # bandera para evitar repeticiones
  71.  
  72. for my $organismo (@organismos) {                               # para todos los organismos
  73.  
  74.     for my $gen (@{$genes_de_organismo{$organismo}}) {          # para todos sus genes
  75.         next if $visto{"$organismo;$gen"}++;                    # excepto si ya lo hemos visto
  76.                                                                 # (caso de un gen que ya participaba en un ortólogo)
  77.  
  78.         ## Iniciamos un bucle que pintará todas las relaciones encontradas
  79.         ## para ese organismo y gen. Debemos repetirlo mientras existan ortólogos posibles para ese gen.
  80.         ## Es importante que sea do(), y no while(): es para los casos de genes sueltos (sin relación con los demás,
  81.         ## el bucle debe ejecutarse al menos una vez, para que salga en salida).
  82.         do {
  83.             ## Buscamos la mayor relación de ortólogos, a partir de ese gen, de ese organismo
  84.             my @ortologos_encontrados = busca_maximo_ortologos("$organismo;$gen");
  85.  
  86.             ## Pintar los ortólogos encontrados
  87.             my @fila = ('') x @organismos;                      # inicializamos a columnas vacías
  88.  
  89.             for my $ort (@ortologos_encontrados) {              # para todos los encontrados
  90.                 my($org,$gen) = split /[;]/, $ort;
  91.                 $fila[$organismo_a_columna{$org}] = $gen;       # ponemos el gen en la columna correspondiente
  92.             }
  93.             say join '', map { sprintf "%-11s", $_ } @fila;     # y pintamos
  94.  
  95.             ## Borrar los ortólogos encontrados.
  96.             ## Debemos destruir los ortólogos que hemos encontrado y pintado,
  97.             ## para que no influyen en el resto de búsquedas (proceso destructivo)
  98.  
  99.             ## El proceso consiste en eliminar los ortólogos que hemos encontrado
  100.             ## de los array de ortólogos relacionados con cada ortólogo encontrado
  101.             ## (esto no queda muy claro, ¿verdad?)
  102.             my $filtro = join '|', map{ quotemeta } @ortologos_encontrados;     # patrón de exp. reg.
  103.  
  104.             for my $ortologo (@ortologos_encontrados) {                         # para todos los ortólogos encontrados
  105.                 my($org,$gen) = split /[;]/, $ortologo;
  106.  
  107.                 next if not exists $ortologos{$ortologo};                       # caso especial:
  108.                                                                                 # ese ortólogo ya fue borrado antes
  109.  
  110.                 # le quitamos a ese ortólogo, todos los ortólogos con los que se relaciona,
  111.                 # que intervienen en el conjunto de ortólogos encontrados
  112.                 $ortologos{$ortologo} = [ grep {! /$filtro/} @{$ortologos{$ortologo}} ];
  113.  
  114.                 # Si ese ortólogo ya no se relaciona con más ortólogos
  115.                 if (@{$ortologos{$ortologo}} == 0) {
  116.                     delete $ortologos{$ortologo};               # lo borramos
  117.                     $visto{$ortologo}++;                        # lo marcamos para no procesarlo más
  118.                 }
  119.             }
  120.         } while ($ortologos{"$organismo;$gen"});                # y repetimos hasta que no haya más relaciones
  121.                                                                 # de ese ortólogo
  122.     }
  123. }
  124.  
  125. ### Proceso recursivo de búsqueda de la máxima cantidad de ortólogos relacionados
  126. ## Vamos llamando a la propia función con un ortólogo más cada vez, hasta que no puede más.
  127. ## Como argumento recibe un array con los ortólogos relacionados encontrados hasta ahora.
  128. ## Devuelve la mayor relación encontrada, o la misma que recibió como argumento, si no puede mejorarla.
  129. sub busca_maximo_ortologos {
  130.     my @ortologos_temporal = @_;
  131.  
  132.     ## Paso 1. Ver si el último ortólogo temporal tiene relación con todos los ortólogos anteriores
  133.     my $ultimo_ortologo = $ortologos_temporal[-1];
  134.  
  135.     if (not exists $ortologos{$ultimo_ortologo}) {              # caso de no existir ninguna relación
  136.         return @ortologos_temporal;                             # regresamos con lo que tenemos
  137.     }
  138.  
  139.     my $nrelaciones = 0;                                        # contaremos el número de relaciones entre ortólogos
  140.     my %organismos_vistos;                                      # cada organismo contará una sola vez
  141.  
  142.     # sacamos el listado de ortólogos con los que se relaciona el último ortólogo
  143.     my %ortologos_ultimo_ortologo = map { $_ => 1 } @{$ortologos{$ultimo_ortologo}};
  144.  
  145.     for my $i (0 .. $#ortologos_temporal-1) {                   # para todos los ortólogos anteriores al último
  146.         my $ortologo_anterior = $ortologos_temporal[$i];
  147.         my($org,$gen) = split /[;]/, $ortologo_anterior;
  148.  
  149.         # si es de un organismo que ya cuenta con un ortólogo entre los ortólogos que estamos analizando
  150.         if ($organismos_vistos{$org}++) {
  151.             delete $ortologos_ultimo_ortologo{$ortologo_anterior};      # no lo vamos a visitar
  152.         }
  153.  
  154.         # si existe una relación entre el último ortólogo, y el anterior
  155.         if ($ortologos_ultimo_ortologo{$ortologo_anterior}) {
  156.             $nrelaciones++;                                             # contamos una relación mas
  157.             delete $ortologos_ultimo_ortologo{$ortologo_anterior};      # y no lo visitaremos (ya lo fue)
  158.         }
  159.     }
  160.  
  161.     # para que el último ortólogo sea legal, debe tener tantas relaciones como ortólogos anteriores a él
  162.     if ($nrelaciones != @ortologos_temporal-1) {                        # no hay relaciones completas con los anteriores
  163.         return @ortologos_temporal[0 .. $#ortologos_temporal-1];        # devolvemos todos menos el último, por ser feo
  164.     }
  165.  
  166.     ## Paso 2. Probar con los ortólogos relacionados con el último ortólogo
  167.     # Hacemos un bucle por todos los ortólogos con los que se relaciona el último ortólogo,
  168.     # y que todavía no han sido visitados
  169.     my @maximo_ortologos;                                               # Variables para recordar el máximo encontrado
  170.  
  171.     for my $prueba_ortologo (keys %ortologos_ultimo_ortologo) {         # para todos los que quedan por visitar
  172.  
  173.         # vemos si ese ortólogo de prueba marca un nuevo record
  174.         my @ortologos_encontrados = busca_maximo_ortologos(@ortologos_temporal, $prueba_ortologo);
  175.  
  176.         if (@maximo_ortologos < @ortologos_encontrados) {               # sí
  177.             @maximo_ortologos = @ortologos_encontrados;                 # lo recordaremos
  178.  
  179.             last if @maximo_ortologos == @organismos;                   # caso de encontrar un ortólogo máximo (extremo)
  180.                                                                         # no hace falta seguir buscando
  181.         }
  182.     }
  183.  
  184.     # Paso 3. Elegir la combinación mayor de lo encontrado hasta ahora
  185.     if (@maximo_ortologos) {                                            # si hemos superado lo encontrado hasta ahora
  186.         return @maximo_ortologos;                                       # devolvemos el récord de ortólogos encontrados
  187.     }
  188.     else {                                                              # si no
  189.         return @ortologos_temporal;                                     # devolvemos lo encontrado hasta ahora
  190.     }
  191. }
  192.  
  193. __END__
Coloreado en 0.006 segundos, usando GeSHi 1.0.8.4
sale esto:
Sintáxis: [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
Gene_1     103485500  550923131  489128838  
Gene_1                550923136            
Gene_2     103485503                        
Gene_3                           489128860  
Gene_4                           489128852  
Gene_5     103485501                        
Gene_6                                      
Gene_7                                      
Gene_8                550923137  489128847  
Gene_8                           489128857  
Gene_8     103485502                        
Gene_9                                      
Gene_10                          489128854  
Gene_10               550923135            
           103485499                        
           103485503             489128844  
           103485504  550923138            
           103485505                        
           103485506             489128842  
           103485507             489128838  
           103485508  550923139  489128857  
                      550923130            
                      550923133            
                      550923134            
                      550923140  489128849  
                                 489128835
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4

Bueno, al menos en este caso, funciona.

En el mundo real... es otra cosa.
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

AnteriorSiguiente

Volver a Bioinformática

¿Quién está conectado?

Usuarios navegando por este Foro: No hay usuarios registrados visitando el Foro y 0 invitados