Datos personales

Mostrando entradas con la etiqueta C#. Mostrar todas las entradas
Mostrando entradas con la etiqueta C#. Mostrar todas las entradas

martes, marzo 25, 2014

Megaevento Gusenet 2014

Tengo el placer de anunciaros que ya tenemos abierto el registro para el megaevento informático del año en España.

más información en http://www.gusenet.org y registro en la misma web.

http://www.gusenet.org

lunes, enero 21, 2013

Alineamientos globales y locales en Bioinformática II - Proyecto Windows 8

Bueno, parece que va tomando forma la aplicación, la estructura la estoy pensando todavía, pero ya puedo ir subiendo un algo de como va a ser:


No se ve con mucha claridad pero ya iré explicando las diferentes partes conforme lo vaya planificando y diseñando.


jueves, enero 17, 2013

Alineamientos globales y locales en Bioinformática I- C Benchmark

Hola, cuanto tiempo no?, sí, tengo el blog descuidado,  me gustaría actualizar más el blog pero debido a los proyectos en los que estoy inmerso y a la firma de un contrato de confidencialidad no puedo publicar nada que esté relacionado con esos proyectos, pero como tengo el hobby de estudiar, lo que voy a hacer es publicar cosas relacionadas con lo que estudio, así que aquí está el primer "post":

Acabo de empezar en el mundillo de la bioinformática y he realizado una versión en C del conocido algoritmo de Needleman y Wunsch para alineamientos globales de secuencias de nucleótidos y proteínas. La decisión de subir el trabajo a la web es por un empujón que me ha dado David Salgado para que lo haga.

Como me ha gustado bastante este mundillo me he planteado migrarlo a C# pero mejorando la primera versión, que la verdad sea dicha, con las prisas me ha salido un poco churro porque no conozco apenas el lenguaje C. (He perdido más tiempo aprendiendo la sintaxis de C que realizando el algoritmo de una manera aceptable.)

Como meta inicial tengo que mejorar estos tiempos:


Que cómo véis tiene un problemilla para secuencias largas, o problemón, 1200 aminoácidos/nucleótidos no son muchos, son más bien pocos si partimos de que un virus puede tener entre 5000 y 800.000 pares de bases, en nuestro caso podríamos tener que comparar un gen de una secuencia de 100.000 letras con otra de 100.000, y eso ya empieza a ser problemático.

Con esto me pongo manos a la obra y pienso. ¿qué necesito?, ¿qué puedo hacer?

La idea que estoy implementando es la siguiente.

-El proyecto está alojado en tfs.visualstudio.com (así de paso lo pruebo y en cuanto tenga algo consistente lo abro a algunos amigos o colegas de profesión como a @xavipaper).
-Lo estoy haciendo en Windows 8 con C# y XAML (lo mismo, probar y aprender).
-Me he bajado MVVM Light para Windows 8 porque lo conozco de Silverlight y me parece un muy buen Framework que me ahorra mucho tiempo.
-Tengo que estudiar todo el tema de paralelismo que puedo encontrar en el blog de Lluis Franco, que es todo un crack en este tema.
-El tratamiento de cadenas tan largas creo que lo tengo más o menos claro creando buffers/doble buffers de entrada.
-Me faltaría estudiar el tratamiento de matrices que se requiere para el algoritmo,

Ya he empezado y estoy haciendo cosas, pero poco a poco, según disponga de tiempo libre, así que para el próximo "post" espero ya poner algo de código.

Un saludo
Oscar

viernes, diciembre 02, 2011

Algoritmo extendido de Euclides

Haciendo algunos ejercicios criptográficos tenía que firmar digitalmente con elGamal los mensajes a enviar y para ello necesitaba calculo el inverso de a módulo n, así que:

os dejo un algoritmo para encontrar el inverso de a módulo n cuando mcd(a,n)=1.

     /// <summary>  
/// Algoritmo extendido de Euclides
/// </summary>
/// <returns>devuelve x tal que ax mod n=1, donde "0<a<n" ></returns>
static private int algoritmo(int a, int n)
{
List<int> g=new List<int>();
g.Add(n); g.Add(a);
List<int> u = new List<int>();
List<int> v = new List<int>();
u.Add(1); v.Add(0);
u.Add(0); v.Add(1);
int i = 1;
while (g[i] != 0)
{
//g[i] = u[i] * n + v[i] * a;
int y = g[i - 1] / g[i];
g.Add(g[i - 1] - y * g[i]);
u.Add(u[i - 1] - y * u[i]);
v.Add(v[i - 1] - y * v[i]);
i++;
}
int x = v[i - 1];
if (x > 0)
{ return x; }
else { return x + n; }
}

sábado, mayo 07, 2011

Traductor catalán-castellano con "scraping"

Si tenéis problemas con el catalán por algún motivo y necesitáis un traductor en tiempo real "by the face", aquí os dejo un extracto de un programilla que traduce del catalán al castellano a partir del traductor de google. Si os fijáis bien en la técnica, se puede modificar para traducir cualquier idioma que soporte el traductor de google ("esta técnica la saqué de un lector "by the face" de cotizaciones de bolsa en tiempo real de yahoo").

Llamada al servicio:

private string llamarServicio(string palabra,string sourceLanguage, string targetLanguage)
{
//palabra: abat
//sourceLanguage: ca
//targetLangauge: es
ASCIIEncoding encoding = new ASCIIEncoding();
string postData = "hl=" + targetLanguage;
postData += ("&sl=" + sourceLanguage);
postData += ("&tl=" + targetLanguage);
postData += ("&q=" + palabra);

WebRequest request = WebRequest.Create(
"http://translate.google.es/?" + postData);
// If required by the server, set the credentials.
request.Credentials = CredentialCache.DefaultCredentials;
// Get the response.
WebResponse response = request.GetResponse();
// Get the stream containing content returned by the server.
Stream dataStream = response.GetResponseStream();
// Open the stream using a StreamReader for easy access.
StreamReader reader = new StreamReader(dataStream, Encoding.GetEncoding("Windows-1252"), true);
// Read the content.
string responseFromServer = reader.ReadToEnd();
// Clean up the streams and the response.
reader.Close();
response.Close();
return responseFromServer;
}

y ahora la llamada la búsqueda del resultado con la expresión regular:

internal string scrapeIdioma(string texto, string cadenaABuscar)
{
//texto es el código fuentes de la página web que nos devuelve la
//función anterior
//cadenaABuscar es la expresión regular:
//"(this.style.backgroundColor='#fff'\">(\\w+))"
Regex _regex;
_regex = new Regex(cadenaABuscar, RegexOptions.Compiled | RegexOptions.IgnoreCase);
Match match = _regex.Match(texto);
if (match.Success && match.Groups.Count>1)
{
return match.Groups[2].Value.ToString();
}
return "";
}

Pues eso, cualquier duda os la resolveré sin problemas.

sábado, julio 10, 2010

Algoritmo C# para dendrograma VI (Datos)

Los datos para hacer pruebas los he sacado de un repositorio público de datos de la UCI: http://archive.ics.uci.edu/ml/ por mediación de la UOC: http://www.uoc.edu para hacer la práctica.

Descripción de los datos:
Title: Acute Inflammations

Abstract: The data was created by a medical expert as a data set to test
the expert system, which will perform the presumptive diagnosis of two
diseases of the urinary system.

----------------------------------------------------------------------------

Data Set Characteristics: Multivariate
Attribute Characteristics: Categorical, Integer
Associated Tasks: Classification
Number of Instances: 120
Number of Attributes: 6
Missing Values? No
Area: Life
Date Donated: 2009-02-11

----------------------------------------------------------------------------

Source:

Jacek Czerniak, Ph.D., Assistant Professor
Systems Research Institute
Polish Academy of Sciences
Laboratory of Intelligent Systems
ul. Newelska 6, Room 218
01-447 Warszawa, Poland
e-mail: jacek.czerniak 'at' ibspan.waw.pl or jczerniak 'at' ukw.edu.pl

----------------------------------------------------------------------------


Data Set Information:

The main idea of this data set is to prepare the algorithm of the expert
system, which will perform the presumptive diagnosis of two diseases of
urinary system. It will be the example of diagnosing of the acute
inflammations of urinary bladder and acute nephritises. For better
understanding of the problem let us consider definitions of both
diseases given by medics. Acute inflammation of urinary bladder is
characterised by sudden occurrence of pains in the abdomen region and
the urination in form of constant urine pushing, micturition pains and
sometimes lack of urine keeping. Temperature of the body is rising,
however most often not above 38C. The excreted urine is turbid and
sometimes bloody. At proper treatment, symptoms decay usually within
several days. However, there is inclination to returns. At persons with
acute inflammation of urinary bladder, we should expect that the illness
will turn into protracted form.

Acute nephritis of renal pelvis origin occurs considerably more often at
women than at men. It begins with sudden fever, which reaches, and
sometimes exceeds 40C. The fever is accompanied by shivers and one- or
both-side lumbar pains, which are sometimes very strong. Symptoms of
acute inflammation of urinary bladder appear very often. Quite not
infrequently there are nausea and vomiting and spread pains of whole
abdomen.

The data was created by a medical expert as a data set to test the
expert system, which will perform the presumptive diagnosis of two
diseases of urinary system. The basis for rules detection was Rough Sets
Theory. Each instance represents an potential patient.

The data is in an ASCII file. Attributes are separated by TAB. Each line
of the data file starts with a digit which tells the temperature of patient.

-- Attribute lines:
For example, '35,9 no no yes yes yes yes no'
Where:
'35,9' Temperature of patient
'no' Occurrence of nausea
'no' Lumbar pain
'yes' Urine pushing (continuous need for urination)
'yes' Micturition pains
'yes' Burning of urethra, itch, swelling of urethra outlet
'yes' decision: Inflammation of urinary bladder
'no' decision: Nephritis of renal pelvis origin

----------------------------------------------------------------------------

Attribute Information:

a1 Temperature of patient { 35C-42C }
a2 Occurrence of nausea { yes, no }
a3 Lumbar pain { yes, no }
a4 Urine pushing (continuous need for urination) { yes, no }
a5 Micturition pains { yes, no }
a6 Burning of urethra, itch, swelling of urethra outlet { yes, no }
d1 decision: Inflammation of urinary bladder { yes, no }
d2 decision: Nephritis of renal pelvis origin { yes, no }

----------------------------------------------------------------------------

Relevant Papers:

J.Czerniak, H.Zarzycki, Application of rough sets in the presumptive
diagnosis of urinary system diseases, Artifical Inteligence and Security
in Computing Systems, ACS'2002 9th International Conference Proceedings,
Kluwer Academic Publishers,2003, pp. 41-51

----------------------------------------------------------------------------

Citation Request:

Please cite:

J.Czerniak, H.Zarzycki, Application of rough sets in the presumptive
diagnosis of urinary system diseases, Artifical Inteligence and Security
in Computing Systems, ACS'2002 9th International Conference Proceedings,
Kluwer Academic Publishers,2003, pp. 41-51

Algoritmo C# para dendrograma V

El algoritmo por fin:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace PR_IA2_2010_Clases
{
static public class Algoritmos
{
///
/// Algoritmo para el cálculo de la distancia Euclidea entre los
/// objetos a partir de los distintos atributos.
///

/// Lista de arrays de strings que representan
/// los atributos de los objetos
/// Una matriz en el intervalo [0,1] de las
/// distancias euclideas entre los objetos

static public double[,] distanciaEuclidea(List datos)
{
try
{
double[,] matriz = null;
//creamos la matriz de distancias en el intervalo [0,1]
//con la distancia media según el nº de atributos (6):
if (datos.Count>0)
{
matriz = new double[datos.Count, datos.Count];
for (int i = 0; i < datos.Count; i++)
{
for (int j= 0; j < datos.Count ; j++)
{
double suma = 0;
for (int k = 0; k < datos[i].Count() - 2; k++)
{
suma+=Math.Pow(double.Parse(datos[i][k])-double.Parse(datos[j][k]),2);
}
double result = Math.Sqrt(suma);
matriz[i, j] = 1-(result/6);
}
}
}
return matriz;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return null;
}
///
/// Algoritmo que calcula la matriz de semejanzas transitiva a partir
/// de una no transitiva.
///

/// Matriz de semejanzas no transitiva
/// Matriz de semejanzas transitiva
static public double[,] clausuraTransitiva(double[,] S)
{
try
{
double[,] R;
do
{
R = (double[,])S.Clone();
S = composicion(R, (double[,])R.Clone());
}while (!iguales(S,R));
return S;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return null;
}
///
/// composición de las semejanzas de una clausura transitiva
///

/// matriz de semejanzas
/// matriz de semejanzas
/// Una matriz de semejanzas
static private double[,] composicion(double[,] R1, double[,] R2)
{
try
{
double[,] S=new double[R1.GetLength(0),R1.GetLength(0)];
for (int x = 0; x < R1.GetLength(0); x++)
{
for (int y = 0; y < R1.GetLength(0); y++)
{
S[x,y] = 0;
for (int z = 0; z < R1.GetLength(0); z++)
{
S[x, y] = Math.Max(S[x,y], Math.Min(R1[x,z],R2[z,y]));
}
}
}
return S;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return null;
}
///
/// Determina si 2 matrices son iguales
///

///
///
///
static private bool iguales(Double[,] S, Double[,] R)
{
try
{
for (int i = 0; i < S.GetLength(0); i++)
{
for (int j = 0; j < S.GetLength(1); j++)
{
if (S[i, j] != R[i, j])
return false;
}
}
}
catch (Exception ex)
{
return false;
}
return true;
}
///
/// Crea un dendrograma a partir de una matriz de semejanzas
/// transitiva.
///

/// matriz de datos
/// Una cadena con el dendrograma
static public string dendrograma(double[,] matriz)
{
try
{
string result="";
List alfa = new List();
List emparejamientos = new List();
//añade los datos alfa de la matriz (resultados).
for (int i = 0; i < matriz.GetLength(0); i++)
{
for (int j = i; j < matriz.GetLength(1); j++)
{
if (!alfa.Contains(matriz[i,j]))
{
alfa.Add(matriz[i, j]);
}
}
}
//ordenamos los datos alfa para ver
//los objetos relacionados.
alfa.Sort();
//recorremos toda la matriz.
for (int x=alfa.Count-1;x>=0;x--)
{
for (int i = 0; i < matriz.GetLength(0); i++)
{
for (int j = i+1; j < matriz.GetLength(1); j++)
{
//Si coincide el valor de la semejanza con
//el valor alfa que estamos tratando,
//añadimos la relación a la cadena final.
if (alfa[x] == matriz[i, j])
{
string strI = "x"+ (i+1).ToString()+" ";
string strJ = "x"+ (j+1).ToString()+" ";
bool existeI = result.Contains(strI);
bool existeJ = result.Contains(strJ);
//sólo añadimos el emparejamiento si
//no existe una relación de emparejamiento
//anterior directa o derivada de otra relación
//de emparejamiento
if (!emparejamientos.Contains(strI + "," + strJ) &&
!emparejamientos.Contains(strJ+","+strI))
{
//se trabaja con 4 supuestos a continuación
//al tratar la relación entre 2 objetos:
if (!existeI && existeJ)
{
emparejamientos = anyadirEmparejamientos(emparejamientos, strI, strJ,
result.Substring(buscarLLaveAbrir(emparejamientos, result, strJ)));
if (result.IndexOf("{" + strJ) > -1)
{
result = result.Replace("{" + strJ, "{{" + strJ);
result += "," + strI + "}";
}
if (result.IndexOf(strJ + "}") > -1)
{
result = result.Insert(buscarLLaveAbrir(emparejamientos,result, strI), "{");
result += "," + strI + "}";
}
}
if (existeI && !existeJ)
{

emparejamientos = anyadirEmparejamientos(emparejamientos, strJ, strI,
result.Substring(buscarLLaveAbrir(emparejamientos,result, strI)));
result = result.Insert(buscarLLaveAbrir(emparejamientos,result, strI), "{");
result += "," + strJ + "}";
}
if (existeI && existeJ)
{
if (result.IndexOf(strI) > result.IndexOf(strJ))
{
emparejamientos = anyadirEmparejamientos(emparejamientos, strI, strJ,
result.Substring(buscarLLaveAbrir(emparejamientos, result, strJ)));
result = result.Insert(buscarLLaveAbrir(emparejamientos, result, strJ), "{");
result = result.Insert(buscarLLaveCerrar(emparejamientos, result, strJ), "}");
result = result.Insert(buscarLLaveAbriryCierreParaComa(emparejamientos, result, strJ) + 1, ",");
}
else
{
emparejamientos = anyadirEmparejamientos(emparejamientos, strI, strJ,
result.Substring(buscarLLaveAbrir(emparejamientos,result, strI)));
result = result.Insert(buscarLLaveAbrir(emparejamientos, result, strI), "{");
result = result.Insert(buscarLLaveCerrar(emparejamientos, result, strI), "}");
result = result.Insert(buscarLLaveAbriryCierreParaComa(emparejamientos, result, strI) + 1, ",");
}
}
if (!existeI && !existeJ)
{
emparejamientos.Add(strI + "," + strJ);
result += ("{" + strI + "," + strJ + "}");
}
}
}
}
}
}
return result.Replace(" ","");
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return "";
}
///
/// Crea una lista de emparejamientos para no duplicar
/// los emparejamientos en el dendrograma final.
///

/// Lista de emparejamientos
/// nuevo objeto
/// objeto existente
/// cadena que engloba los objetos que se emparejan
/// con todos los objetos que se relacionan con ellos
/// Devuelve la lista de emparejamientos
static private List anyadirEmparejamientos(List emparejamientos,string nuevo, string J,
string trozo)
{
try
{
char[] caracteresDelimitadores = { '{','}',',' };
string[] filas;
filas = trozo.Split(caracteresDelimitadores, StringSplitOptions.RemoveEmptyEntries);
//mediante una array añado todos los objetos relacionados
//a lista de emparejamientos.
for (int i = 0; i < filas.Count(); i++)
{
if (!emparejamientos.Contains(nuevo+','+filas[i])
&& nuevo!=filas[i])
{
emparejamientos.Add(nuevo + ',' + filas[i]);
}
for (int j = 0; j < filas.Count(); j++)
{
if (!emparejamientos.Contains(filas[i] + ',' + filas[j])
&& !emparejamientos.Contains(filas[j] + ',' + filas[i]) &&
filas[i]!=filas[j])
{
emparejamientos.Add(filas[i] + ',' + filas[j]);
}
}
}
return emparejamientos;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return null;
}
///
/// Busca la llave de abrir para hacer un emparejamiento
///

/// Lista de emparejamientos
/// dendrograma final
/// Objeto a buscar
/// La posición de la primera llave para el
/// emparejamiento

static private int buscarLLaveAbrir(List emparejamientos,string result, string I)
{
try
{
int min = result.Length;
var lista= from e in emparejamientos
where e.IndexOf(I)>-1
select e;
//dentro de todos los emparejamientos de un objeto, obten-
//dremos el que esté en el lado más izquierdo del dendrograma
foreach (string str in lista)
{
if (result.IndexOf(str.Substring(0, str.IndexOf(","))) < min &&
result.IndexOf(str.Substring(0, str.IndexOf(","))) > -1)
min = result.IndexOf(str.Substring(0, str.IndexOf(",")));
if (result.IndexOf(str.Substring(str.IndexOf(","))) < min &&
result.IndexOf(str.Substring(str.IndexOf(","))) > -1)
min = result.IndexOf(str.Substring(str.IndexOf(","))) - str.Substring(0, str.IndexOf(",")).Length;
}
return min;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return 0;
}
///
/// Busca la llave de cerrar para hacer un emparejamiento
///

/// Lista de emparejamientos
/// dendrograma final
/// Objeto a buscar
/// La posición de la última llave para el
/// emparejamiento

static private int buscarLLaveCerrar(List emparejamientos, string result, string I)
{
try
{
int max =0;
var lista = from e in emparejamientos
where e.IndexOf(I) > -1
select e;
//dentro de todos los emparejamientos de un objeto, obten-
//dremos el que esté en el lado más derecho del dendrograma
foreach (string str in lista)
{
if (result.IndexOf(str.Substring(0,str.IndexOf(","))) > max)
max = result.IndexOf(str.Substring(0, str.IndexOf(","))) + str.Substring(0, str.IndexOf(",")).Length;
if (result.IndexOf(str.Substring(str.IndexOf(",")+1)) > max)
max = result.IndexOf(str.Substring(str.IndexOf(",") + 1)) + str.Substring(0, str.IndexOf(",")).Length;
}
return max;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return 0;
}
///
/// Dentro de cada emparejamiento, busca la posición intermedia de la
/// relación para insertar la coma de separación que deja el dendrograma
/// más claro de entender.
///

/// Lista de emparejamientos
/// dendrograma final
/// Objeto a buscar
/// La posición intermedia del emparejamiento
static private int buscarLLaveAbriryCierreParaComa(List emparejamientos, string result, string I)
{
try
{
int min = buscarLLaveAbrir(emparejamientos,result,I);
int numLlaveAbrir=1;
for (int i = min; i >= 0; i--)
{
if (result.Substring(i, 1) == "{")
numLlaveAbrir++;
else
break;
}
for (int i = min; i < result.Length; i++)
{
if (result.Substring(i, 1) == "}")
numLlaveAbrir--;
if (numLlaveAbrir == 0)
return i;
}
return min;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return 0;
}
}
}

Algoritmo C# para dendrograma IV

La parte Datos.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace PR_IA2_2010_Clases
{
static public class Datos
{
///
/// Normalizamos los datos aplicando ranging a la primera
/// columna y un valor binario a las posteriores.
///

///
/// Una lista normalizada de arrays de strings
static public List Normalizar(List datos)
{
try
{
//normalizamos los datos:
if (datos != null && datos.Count > 0)
{
//sumamos la primera fila para aplicar ranging.
float maximo = float.MinValue;
float minimo = float.MaxValue;
for (int i = 0; i < datos.Count; i++)
{
float result;
if (float.TryParse(datos[i][0].Replace('.', ','), out result))
{
if (result < minimo)
minimo = result;
if (result > maximo)
maximo = result;
}
}
foreach (string[] fila in datos)
{
//ranging a la primera columna:
float result;
if (float.TryParse(fila[0].Replace('.', ','), out result))
{
fila[0] = ((result - minimo) / (maximo - minimo)).ToString();
}
for (int i = 1; i < fila.Count(); i++)
{
//comprobamos si hay valores binarios
if (fila[i].ToUpper() == "YES" || fila[i].ToUpper() == "SÍ")
{
fila[i] = "1";
}
if (fila[i].ToUpper() == "NO")
{
fila[i] = "0";
}
}
}
}
return datos;
}
catch (Exception ex)
{
new Exception(ex.Message);
}
return null;
}
}
}

Algoritmo C# para dendrograma III

Aquí la parte de código de IO.cs:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace PR_IA2_2010_Clases
{
static public class IO
{
///
/// Lectura de los datos de un fichero dado de tipo CVS que
/// transforma en una lista de arrays de tipo string.
///

/// fichero
/// Devuelve una lista de arrays de tipo string
static public List leerDatos(string fichero)
{
string texto;
string[] filas;
List datos=null;
try
{
System.IO.StreamReader sr =
new System.IO.StreamReader(fichero, System.Text.Encoding.Default, true);
texto = sr.ReadToEnd();
string[] caracteresDelimitadores = {"\r\n"};
//Creamos un lista de arrys de una forma rápida para
//tener cada dato por separado para su posterior tratamiento.
filas=texto.Split(caracteresDelimitadores,StringSplitOptions.RemoveEmptyEntries);
if (filas.Count()>0)
{
datos=new List();
for (int i = 0;i< filas.Count(); i++)
{
datos.Add(filas[i].Split(','));
}
}
sr.Close();
return datos;
}
catch (System.IO.IOException ex)
{
throw new Exception(ex.Message);
}
catch (System.Exception ex)
{
throw new Exception(ex.Message);
}
return null;
}
}
}

jueves, junio 24, 2010

Algoritmo C# para dendrograma II

//El código del proceso principal para testear los algoritmos:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using PR_IA2_2010_Clases;

namespace PR_IA2_2010
{
class Program
{
static void Main(string[] args)
{
List datos;
if (args.Count() == 0)
{
//sin parámetros
Console.WriteLine("Por defecto se analiza diagnosis3.csv");
Console.WriteLine("Si quiere otro fichero debe escribir:");
Console.WriteLine("PR_IA2_2010.EXE nombre_fichero_con_datos");
datos =
IO.leerDatos("diagnosis3.csv");
}
else
{
//Si ponemos un parémetro es el nombre del fichero.
datos =
IO.leerDatos(args[0]);
}
DateTime tiempoInicio = DateTime.Now;
//normalizamos:
datos = Datos.Normalizar(datos);
//calculamos la media de las distancia euclidea entre
//los objetos
double[,] R = Algoritmos.distanciaEuclidea(datos);
//Calculamos la semejanza entre ellos
double[,] semejanza = Algoritmos.clausuraTransitiva(R);
Console.WriteLine("El resultado es: ");
//creamos el dendrograma con el resultado obtenido.
Console.WriteLine(Algoritmos.dendrograma(semejanza));
Console.WriteLine("Tiempo= " + DateTime.Now.Subtract(tiempoInicio));
Console.ReadKey();
}
}
}

jueves, junio 17, 2010

Algoritmo C# para dendrograma I

He creado un algoritmo para el cálculo de dendrogramas según el método de clausura transitiva para la asignatura de Inteligencia Artificial II de la carrera de Ingeniería Informática en el Universitat Oberta de Catalunya. Como no me gusta quedármelo para mí solo y supongo que los profes no se mosquearán, aquí os escribo una serie de artículos dónde expongo una breve explicación: artículo I y los fuentes: artículos siguientes.

Tanto el algoritmo como el programa de prueba lo he realizado con C# y Framework 3.5 con el entorno de desarrollo Visual Studio 2008.

Para realizar el algoritmo y probarlo he creado 2 proyectos diferentes englobados en una solución que me permite probar , ejecutar y modificar el código.

Los proyectos son:
• PR_IA2_2010
Proyecto de inicio que usa la librería PR_IA2_2010_Clases para el cálculo del problema propuesto. Este proyecto presenta el resultado final:
o Program.cs: es el módulo principal donde se encuentra Main. Desde este módulo se llaman a los distintos algoritmos para la resolución del problema.

• y PR_IA2_2010_Clases
Conjunto de clases dónde se encuentran los algoritmos desarrollados para la resolución del problema. He creados 3 partes distintas entre sí para que la lectura del código se más clara.
o IO.cs: Tiene los métodos de lectura de los datos.
static public List leerDatos(string fichero)
Lectura de los datos de un fichero dado de tipo CVS que transforma los atributos de los objetos en una lista de arrays de tipo string
o Datos.cs: Tiene los métodos de transformación de los datos (normalización)
static public List Normalizar(List datos)
Normalización de lso datos aplicando ranging a la primera columna y un valor binario a los posteriores atributos.
o Algoritmos.cs: Algoritmos de la aplicación.
static public double[,] distanciaEuclidea(List datos)
Algoritmo para el cálculo de la distancia Euclidea entre los objetos a partir de los distintos atributos.
static public double[,] clausuraTransitiva(double[,] S)
Algoritmo que calcula la matriz de semejanzas transitiva a partir de una matriz no transitiva.
static private double[,] composicion(double[,] R1, double[,] R2)
Composición de las semejanzas de una clausura transitiva.
static private bool iguales(Double[,] S, Double[,] R)
Determina si 2 matrices de semejanzas son iguales.
static public string dendrograma(double[,] matriz)
Crea un dendrograma a partir de una matriz de semejanzas transitiva.
static private List anyadirEmparejamientos(List emparejamientos,string nuevo, string J, string trozo)
Crea una lista de emparejamientos para no duplicar los emparejamientos en el dendrograma final.
static private int buscarLLaveAbrir(List emparejamientos,string result, string I)
Busca la llave de abrir para hacer un emparejamiento.
static private int buscarLLaveCerrar(List emparejamientos, string result, string I)
Busca la llave de cerrar para hacer un emparejamiento
static private int buscarLLaveAbriryCierreParaComa(List emparejamientos, string result, string I)
Dentro de cada emparejamiento, busca la posición intermedia de la relación para insertar la coma de separación que deja el dendrograma más claro de entender.

En el próximo artículo empezaré a mostrar el código.

jueves, diciembre 03, 2009

Oferta empleo Programador Junior

Hola a todos, se oferta un puesto de trabajo “programador junior?” con las siguientes características.

-Necesitamos una persona dinámica, con ganas de aprender y en continúo reciclaje y que considere que pueda con las siguientes tareas a desarrollar en el dpto. de programación:
-Asistencia telefónica con el cliente en 2ª línea. (la primera es al que recibe la llamada y si no sabe resolverla la pasa a la 2ª).
-Mantenimiento de aplicaciones VB6, SQL Server 2000/2005, C#, VB9, Visual Studio 2008, Framework 3.5 (normalmente la llamada es por algún error de programación que hay que detectar, debido a las continuas modificaciones en las aplicaciones, ahora se contabilizan unas 8 llamadas diarias por personas e incluso menos)
-Posibilidad de viajar al menos una vez al mes (es raro que se viaje, pero existe la posibilidad de testear nuevas aplicaciones, arreglar errores in situ, etc..)
-Cómo requisito imprescindible es coche propio con carnet de conducir, residencia en la provincia de Alicante, que sea organizada y al menos que tenga el título de DAI, esté cursando o similar.

Si queréis más información podéis mandarme un mail.

Un saludo a todos.

martes, octubre 20, 2009

Combobox y ToString()

Andaba líado con una clase de poblaciones de España que contenía una descripción y un código llamado INE, que es el código que representa a una población según el INE (Instituto Nacional de Estadística):

...
private string _CodigoIne;
private string _Localidad;
...

e intentando a través de otra clase que me devolviera una lista de poblaciones leyéndola de la base de datos a través del método:

public List lista(){....}

no había forma de que me presentara los nombres de las poblaciones en el combobox aunque se lo marcara en la propiedad DisplayMember del combobox susodicho:

cbLocalidad.DataSource = bsLocalidad;
cbLocalidad.DisplayMember = "Localidad";
cbLocalidad.ValueMember = "CodigoINE";

pero como dirían los gallegos, depende, a veces sí a veces no aparecía el nombre y otras el nombre de la clase:

Entidades.MaestroLocalidad
Entidades.MaestroLocalidad
Entidades.MaestroLocalidad

en vez de por ejemplo:

Alicante
Elche
Santa Pola

así que decidí esta mañana sobreescribir el método ToString() de la clase mencionada en primer lugar:

public override string ToString()
{
return _Localidad;
}

y solucionado el problema.

Un saludo
Oscar Montesinos

miércoles, septiembre 23, 2009

Menú con lista de ventanas

Algo que parece tan complicado a simple vista como es la de gestionar un menú de formularios hijos abiertos (MDI-MDIChild), se convierte en una tarea fácil con nuestro querido .NET framework, pero ojo, no publico este post porque sea algo tan sencillo, no!!!, lo publico porque he encontrado una notable diferencia entre .NET framework 2.0 y .NET framework 3.5 que puede liar la madeja durante un buen rato (por cierto que buena está la madeja de cordero).

Ahora al grano, para Framework 2.0 tenemos que añadir un menú del cuadro de herramientas llamado MainMenu (obsoleto) y añadir sus correspondientes MenuItems, en el que uno de ellos sería por ejemplo "Ventanas", y al que tenemos que poner la propiedad MDIList a true.

Para Framework 3.5 la cosa ha cambiado, ya no tenemos el menú MainMenu, y como habréis podido leer en el link que os he puesto en MainMenu, Microsoft nos aconseja que usemos MenuStrip en vez de MainMenu. Y ahora ya nos podríamos volver locos buscando lo de MDIList porque aquí esa propiedad no existe. En este control lo que nos han puesto es una propiedad llamada MdiWindowsListItem que nos permite seleccionar un ToolStripMenuItem que hayamos creado en el Menú ToolStrip.

Y con esto nada más por ahora, y que malo es no saber, porque he perdido un poquillo de tiempo por esta chorrada, casi me creo yo mismo el gestor del menú de ventanas y eso no me sale rentable.

Un saludo
Oscar Montesinos

domingo, julio 26, 2009

C# ProcessStartInfo y Process

Un truquillo para ejecutar aplicaciones desde un programilla y que se quede en espera hasta que éste termine (pasando parámetros):







y aquí si quieres copiar y pegar:

ProcessStartInfo startInfo = new ProcessStartInfo("c:\\windows\\notepad.exe");
startInfo.Arguments = "c:\\UnFichero.txt";
startInfo.WindowStyle = ProcessWindowStyle.Normal;
Process process=new Process();
process.StartInfo=startInfo;
process.Start();
process.WaitForExit();
process.Close();

Un saludo
Oscar Montesinos

viernes, julio 24, 2009

LINQ a XML con namespace

Hoy toca una rápida.

Al intentar consultar un XML generado por la competencia mediante LINQ por el procedimiento tradicional, me ha pasado que no me encontraba nada cuando en los XML generados por nuestra aplicación si me encuentra los elementos que busco mediante la siguiente instrucción:





Revisando el xml que genera la competencia y comparándolo con el nuestro me he dado cuenta que en la cabezar usa el atributo xmlns, es decir, que usa namespace para el nombre de cada elemento:











Así que la cosa cambia, porque un elemento que dependa del raiz DOCS_NOT ya no se llama tal cual lo vemos, se llama por ejemplo , así que la búsqueda mediante linq cambiará a:





es decir, que de alguna manera hay que indicarle el namespace.

Pues nada más, saludos a todos y a divertirse...

Un saludo
Oscar Montesinos.




martes, julio 21, 2009

Proyecto e-Dni

Os dejo el link con los screenshots del proyecto e-DNI que estoy a punto de terminar. Ya está en fase de pruebas:

http://www.facebook.com/photo.php?pid=30324446&l=2fb71f0f08&id=1592291277

El proyecto está hecho en C#, Framework 3.5 contra una bd en SQL Server compatible con 2000.

Un saludo
Oscar Montesinos.

jueves, marzo 19, 2009

WINFORM: Cambiar TAB por INTRO

Pues sí, he decidido escribir este texto recopilando todo lo que me he encontrado ultimamente por ahí y que pegas hay.

Para empezar recuerdo que desde tiempos inmemoriables se ha usado SENDKEYS para susodicha tarea, pero también recuerdo que si pones en google SENDKEYS podrás ver que hay infinidad de páginas que indican problemas varios con esta instrucción. Un ejemplo es que en determinados portátiles no funciona y otro problema es que borra el buffer del teclado, etc...

Buscando sustituto me he ido a esta página
http://www.gamarod.com.ar/trucos/enviar_la_tecla_tab_sin_los_problemas_del_sendkeys.asp
(que por cierto, tarda un montón en cargarse), para ver que se puede usar la función "keybd_event" de la api "user32.dll".

He buscado información en MSDN:
http://msdn.microsoft.com/en-us/library/ms646304(VS.85).aspx
y leyendo atentamente me comenta que no use esta función que ha sido reemplazada por SendInput, la cual podéis encontrar en msdn en este link:
http://msdn.microsoft.com/en-us/library/ms646310(VS.85).aspx
que además de enviar teclas permite enviar pulsaciones y movimientos del ratón, y además no resetea el estado del teclado.
Como siempre he pensado que la MSDN está un poco complicada para la gente normal y corriente pues he seguido investigando esta función y he encontrado esta maravillosa página hecha expresamente para gente como yo:
http://www.pinvoke.net/default.aspx/user32.SendInput
cuyo site voy a tener entre mis links preferidos.

De todas formas, al final no he usado ninguna de las 3 porque necesito saber en mi programa hacia que control va a saltar el TAB para realizar determinadas opciones y la única forma que he encontrado es guardar un list de los controles del formulario con el orden de tabulación preestablecido,

martes, enero 06, 2009

Lector RSS en C# 3.5 y LINQ

(Este artículo tiene otro punto de vista en este otro que creo mejora este sistema: http://oscarmontesinos.blogspot.com/2009/08/lector-rss-con-framework-35-sin-linq.html)

Retomando mi actividad normal diaria, me he encontrado con una clase para leer RSS que tenía por ahí guardada y que he retocado para usar LINQ.

Primero he creado una clase con los atributos que necesito y a la que he llamado Articulo:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

public class Articulo
{
public DateTime Fecha;
public string Titulo;
public string Contenido;
public string Enlace;
public Articulo()
{
}
public Articulo(DateTime pFecha, string pTitulo, string pContenido, string pEnlace)
{
Fecha = pFecha;
Titulo = pTitulo;
Contenido = pContenido;
Enlace = pEnlace;
}
}

Luego he creado una clase para leer las RSS y que consta de 2 métodos:
  • uno público que es el punto de entrada y dónde le pasamos una lista de cadenas que representa cada una de ellas una dirección de subscripción a una RSS
  • uno privado que es el que se encarga de ir leyendo cada servidor de noticias.
Aquí el código:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Xml;
using System.Xml.Linq;
using JPA.XML.Clases.Entidades;

public class LectorRSS
{
public List CargarRSS(List feeds)
{
//Ejemplos de links
//List feeds = new List
//{
// "http://noticiasjpa.blogspot.com/feeds/posts/default",
// "http://dnnotaword.blogspot.com/feeds/posts/default",
//};
List articulos = new List();
foreach (String sFeed in feeds)
{
leerRSS(articulos,sFeed);
}
return articulos;
}
private void leerRSS(List articulos, string sFeed)
{
try
{
//cargamos el XML a leer.
var feed = XDocument.Load(sFeed);
//la consulta en LINQ:
var result = from c in feed.Root.Elements()
where c.Name.LocalName == "entry" //Selecciono sólo las entradas
select new Articulo //por cada entrada creo un objeto Artículo.
{
Fecha = c.Elements().Where(Fecha => Fecha.Name.LocalName == "published").
Select(Fecha => DateTime.Parse(Fecha.Value)).First(),
Titulo = c.Elements().Where(Titulo => Titulo.Name.LocalName == "title").
Select(Titulo => Titulo.Value).First(),
Contenido = c.Elements().Where(Contenido =>Contenido.Name.LocalName == "content").
Select(Contenido => Contenido.Value).First(),
Enlace = c.Elements().Where(Enlace => Enlace.Name.LocalName=="link").
Select(Contenido => Contenido.Attribute("href").Value).Last()
};
articulos.AddRange(result);
//A continuación tenéis el código sustituído:
//foreach (XElement xElement in ListaArticulos)
//{
// if (xElement.Name.LocalName == "entry")
// {
// Articulo articulo = new Articulo();
// foreach (XElement xElement2 in xElement.Elements())
// {
// switch (xElement2.Name.LocalName)
// {
// case "title":
// articulo.Titulo = xElement2.Value;
// break;
// case "content":
// articulo.Contenido = xElement2.Value;
// break;
// case "published":
// articulo.Fecha = DateTime.Parse(xElement2.Value);
// break;
// case "link":
// foreach (XAttribute xAttribute in xElement2.Attributes())
// {
// if (xAttribute.Name == "href")
// {
// articulo.Enlace = xAttribute.Value;
// }
// }
// break;
// }
// }
// if (articulo.Contenido.Trim() != "")
// {
// articulos.Add(articulo);
// }
// }
//}
}
catch (Exception ex)
{
throw new Excepciones.LectorRSS(ex.Message);
}
}
}

martes, diciembre 02, 2008

Factorizar un número por el método de los primos

Aquí tenéis el código en C# para factorizar un nº que le pasé a Eugenio Estrada en un reto que planteó hace poco:

private ArrayList ObtenerMultiplos(ulong Numero)
{
ArrayList al = new ArrayList();
int aumentar = 4;
if (Numero == 1)
return null;
if (Numero == 2 || Numero == 3)
{
al.Add(Numero);
return al;
}
while (Numero % 2 == 0)
{
al.Add(2);
Numero/=2;
}
while (Numero % 3 == 0)
{
al.Add(3);
Numero /= 3;
}
ulong factorial = 24;
ulong i = 5;
while ((i <= Math.Sqrt(Numero) + 1) && Numero != 1)
{
if (((factorial+1) % i == 0) && (Numero % i == 0))//es primo y divisible por i
{
while ((Numero % i) == 0)
{
al.Add(i);
Numero = Numero / i; //vamos añadiendo mientras sea divisible.
}
}
else
{
if (aumentar == 2)
{
factorial = factorial * (i) * (i + 1) * (i + 2) * (i + 3);
aumentar = 4;
}
else
{
factorial = factorial * (i) * (i + 1);
aumentar = 2;
}
}
i += (ulong)aumentar;
}
if (Numero>1) al.Add(Numero);
return al;
}


El algoritmo lo saqué de la wikipedia.

Etiquetas

.net (1) ALGORITMO (4) algoritmos (1) Android (1) angular (2) aplicaciones WEB (1) ARGENTINA (1) ASP (4) asp .NET (1) ASP .NET Identity (1) attach (1) Azure (1) base de datos (1) BINDING (1) BioInformática (2) bootstrap (1) C (2) C# (27) castellano (1) catalán (1) Charla (1) CheckedListBox (1) Clase (1) clausura transitiva (2) CLIENTES (1) Closing (1) Combobox (1) Comisiones (1) CONCURSO (1) condones (1) consultas (1) corrupta (1) CORS OWIN (1) CORS WEB API 2 (1) Criptografía (1) CUENTA NARANJA (1) Custom Control (1) Daniel Seara (1) DATAGRIDVIEW (1) David Salgado (2) dendrograma (6) depurar (1) desarrollo (1) Deserializar (1) DEVCAMP (2) durex (1) e-DNI (1) el Guille (2) Eladio Rincón (1) elGamal (1) encriptación (1) encuesta (1) Entidad (1) ERROR (2) error 3624 (1) España (1) España es nido de víboras. (1) Euclides (1) Euclides extendido (1) evento (1) eventos. (1) factorización (1) factorizar (1) física (1) Framework 2.0 (1) Framework 3.5 (5) Framework 4 (2) Francisco González (1) Francisco Ruiz (1) GO (1) google (1) gossip (1) Grupos de usuarios (1) Guadalajara (1) Guille Comunity Tour (2) Gusenet (9) GUSENET. (1) Huelga informáticos (1) IBEX 35 (1) Idioma (1) IFT (1) IISExpress (1) Indice de Fuerza Tecnica (1) informática (1) Informix (1) ING DIRECT (1) INGDIRECT (1) Ingeniería Informática (2) Inteligencia artificial (5) Intro (1) IOS (1) IPad (1) IPhone (1) IV Aniversario (1) JavaScript (2) JPA (2) keybd_event (1) LA CAIXA (1) La Pineda (1) ladroentidad (1) Lector RSS (2) LINQ (5) LINQ2XML (1) ListBox (1) Live Distributed Objects (1) llenar (1) LOG (1) Madrid .NET (1) MainMenu (1) MAP (1) MAP 2011 (1) MAR DEL PLATA (1) matemáticas (1) Matriculación (1) MDIList (1) MdiWindowsListItem (1) MenuItem (1) MenuStrip (1) Microsoft (18) Microsoft Active Professional (1) Miguel Egea (2) MSDE 2 (1) MSDE 2000 (1) MVVM Light (2) mysql (1) NAMESPACE (1) Needleman (2) NET (1) NS (1) Oferta empleo (1) Office 14 (1) Office 2007 (1) Office 2009 (1) ON ERROR (1) OOB (1) Oscar Montesinos (1) OWIN (1) OWIN Security middleware (1) Paginación (1) PDC (1) Pedro Hurtado (1) PINTARTECA (1) PrinterSettings (1) Process (1) ProcessStartInfo (1) Programador (1) Relacional (1) robo (1) RSS (1) Rubén Garrigós (1) Salvador Ramos (1) Santa Pola (1) scrape (1) scraping (1) ScrollBar (1) Secretaría (1) SendInput (1) SENDKEYS (1) Sergio Vázquez (1) Serializar (1) Silverlight 2.0 (2) Silverlight 4 (1) Silverlight 5 (3) Silverlight. (1) Sindicado (1) Sistema Personal de Trading (3) Sistemas Distribuidos (1) SOLID SUMMIT 2009 (1) SPT (2) SQL Server (3) SQL Server 2000 (2) SQL Server 2005 (2) SQL Server 2008 (3) SQL Server Denali (1) SQL Server Information Services. (1) SQLU (1) SSIS (1) SUMMIT SQL (1) Suspect (1) Syndication (1) TAB (1) Tablas (1) Tarragona (1) Token bearer (1) ToolStripMenuItem (1) ToString() (1) Traductor (1) transacciones (1) treeview (1) truco (1) TRY CATCH (1) UCI (1) Unience (2) Universad (1) Universidad Oberta Catalunya (2) UOC (8) Usuarios. (1) VB (1) VB6 (1) VB9 (1) VIAJAR (1) Vila-seca (1) VISUAL BASIC (3) Visual Basic. (1) visual studio (1) Visual Studio 2005 (1) Visual Studio 2008 (16) Visual Studio 2010 (2) Visual Studio 2013 (1) VS2010 (1) VSTA (1) VSTO (1) WCF (1) WEB API (1) web.config (1) WebClient (1) WF (1) windows (1) Windows 7 (3) Windows 8 (2) Windows Azure (1) Windows pone (1) Windows Server 2008 (1) Windows Vista (1) woff (1) WP7 (1) WPF (1) Wunsch (2) XAML (4) XDocument (1) XElement (1) XML (3) XNA (1) Yield (2)