ABSTRACT: Se hizo un software que fuera capaz de detectar un error en una cadena de caracteres a travs de cdigo hamming, para lo cual se bas en el diseo con lenguaje C, y Dev Cpp, como compilador. Adems de hacer uso de este, se logra entender el algoritmo y el funcionamiento de estos.
Keywords: Detector de errores, Codigos hamming, codigos por paridad
INTRODUCCIN
Lo que nosotros denominamos como comunicacin tiene como eje central un flujo de informacin a travs de un sistema. Pero en la prctica, a la hora de realizar una transmisin surgen gran cantidad de problemas, por los cuales se necesario utilizar tcnicas que permitan detectar y corregir los errores que se hayan producido en esta. Esta serie de tcnicas estn basadas en la idea de aadir en bits cierta informacin redundante a la informacin que desee enviarse. A partir de ella el receptor puede determinar, de forma bastante fiable, si los bits recibidos corresponden realmente a los enviados.
OBJETIVOS
2.1 OBJETIVO GENERAL
Implementar un software a travs del lenguaje C, el cual nos permita establecer la veracidad de la informacin que se pretenda enviar.
.
Si en la transmisin de la palabra cdigo se produce un solo error, la paridad de la palabra cdigo cambiar y coincidir con la del bit de parida. Por lo tanto, se detectar el error. Sin embargo, si hay dos errores, la paridad ser la misma y el error no s detectar. Deducimos, pues, que con el bit de paridad el cdigo permite detectar un nmero impar de bits errneos. 3.1.1 CDIGOS BLOQUE LINEALES La salida de una fuente de informacin es una secuencia de dgitos binarios "0" o "1". En la codificacin de bloque, esta secuencia de informacin binaria es segmentada en bloques de mensaje de una longitud fija; cada bloque de mensaje, llamado u, consiste en k dgitos de informacin. Hay un total de 2k mensajes distintos. El codificador, de acuerdo con ciertas reglas, transforma cada mensaje entrante u, en una palabra binaria de n bits, v, con n > k. V es lo que llamamos palabra cdigo ( o vector cdigo) del mensaje u. Por lo tanto, para los 2k posibles mensajes, hay 2k palabras cdigo. A este conjunto de 2k palabras cdigo, se le llama Cdigo bloque. Para que un cdigo bloque sea til, las 2k palabras cdigo deben ser distintas. En consecuencia, tiene que haber una correspondencia uno a uno entre un mensaje u y su palabra cdigo v. Una estructura que se desea que tenga un cdigo bloque, es la linealidad . Con esta estructura, la complejidad de la codificacin se reduce enormemente, como veremos ms adelante. A un cdigo bloque de longitud n y 2k palabras cdigo se le llama cdigo lineal (n,k) si y slo si sus 2k palabras cdigo forman un subespacio k-dimensional. De hecho, un cdigo binario es lineal si y slo si la suma de mdulo 2 de dos palabras cdigo es tambin una palabra cdigo. El bloque cdigo dado en la siguiente tabla (Tabla 1) es un cdigo lineal (7,4). Se puede comprobar fcilmente que la suma de dos palabras cdigo en este cdigo es tambin otra palabra cdigo. desde 1 hasta 2m-1, los bits en la posicin 2k, donde , son los bits de paridad y los bits restantes son bits de informacin. El valor de cada bit de paridad se escoge de modo que el total de unos en un nmero especfico de bits sea par, y estos grupos se escogen de tal forma que ningn bit de informacin se cubra con la misma combinacin de bits de paridad. Es lo anterior lo que proporciona al cdigo su capacidad de correccin. Para cada bit de paridad en la posicin 2k, su grupo de bits de informacin correspondiente incluye todos esos bits de informacin correspondiente cuya representacin binaria tenga un uno en la posicin 2k. Por otra parte, un cambio de dos bits en una palabra del cdigo no cambia el valor del bit de paridad si ambos bits pertenecen al mismo grupo de paridad. Sin embargo ello no es posible ya que para dos posiciones cualquiera de una palabra del cdigo siempre hay un grupo de paridad que no incluye ambas posiciones. En otras palabras, como dos bits cualquiera deben estar en distintas posiciones, sus nmeros binarios deben diferir al menos en un bit, as que siempre hay al menos un grupo de paridad con un solo bit cambiado, lo cul da lugar a una palabra que no pertenece al cdigo con al menos un valor de paridad incorrecto.
#include <stdio.h> #include <stdlib.h> #include <math.h> #include <string.h> typedef struct nodo { int bit; struct nodo *sig; } lista; lista *cabeza=NULL;
.
int charInt(char); int *convertirLista(lista *cab,int longitud); void crear(struct nodo **cabeza); void insertarNodo(int dato); void insertarElNodo(struct nodo *actual, struct nodo *nuevo); int *hallarBitsParidad(int,int*,int, int* paridad); int longitudHam(int lonHam); short esPar(int num); int main(int argc, char *argv[]) { short opcion=0; do{ printf("\nIngrese el numero de la opcion dependiendo de lo que usted desea:\n "); printf("1. Enviar una palabra en binario y mostrar como queda despues de\n pasar por el codigo de Hamming\n "); printf("2. Ingresar una palabra recibida en codigo Hamming, buscar errores,\n mostrarlos, corregirlos y entregar la palabra decodificada\n "); printf("3. Salir\n\n\n"); scanf("%d",&opcion); if(opcion==1){ while(getchar()!='\n');//libera el buffer system("cls"); printf("Ingresar una palabra en binario:\n char ch; int contador=0, i=0; //recibe caracter por caracter, revisa si es binario y envia un nodo con el valor al final de la lista while( (ch=getchar())!='\n' ){ i=charInt(ch); if(i!=0 && i!=1); else{ insertarNodo(i); contador++; } } int lonPal=contador; int palabra[lonPal]; int lonHam=longitudHam(lonPal); //a partir de la longitud de la palabra hlla el tamao q tendra codificada int k=0, temp=0, lonParidad=0; int Hamm[lonHam]; lista *aux; //convertir de lista a cadena for(aux=cabeza,i=0;aux!=NULL;aux=aux->sig){ palabra[i]=aux->bit; i++; } //crear la cadena hamming asignando un 4 a las posiciones de paridad temp=3; while(temp<lonHam){ if(temp-1!=2) Hamm[temp-1]=4; temp=pow(2,k); k++; lonParidad++; } //se asignan las posiciones de datos a la cadena en Hamming int j=0; for(i=0; i<lonHam ; i++){ if(Hamm[i]!=4){ Hamm[i]=palabra[j]; j++; } } //hallamos los bits de paridad int paridad[lonParidad]; int *array=hallarBitsParidad(lonHam,Hamm,lonParidad,paridad); for(i=0;i<lonParidad;i++) paridad[i]=*(array+i); //asignamos los bits de paridad j=0; for(i=0; i<lonHam ; i++){ if(Hamm[i]==4){ Hamm[i]=paridad[j]; j++; } } //imrpimir palabra codificada printf(" \nPalabra Codificada\n "); for(i=0; i<lonHam ; i++) printf("%i", Hamm[i]); printf("\n"); }else{ if(opcion==2){ //DECODIFICAR while(getchar()!='\n');//libera el buffer printf("\n Ingrese una palabra en binario para ser decodificada:\n " ); char ch; int contador=0, i=0,num,lonParidad=0; cabeza=NULL; //recibe caracter por caracter, revisa si es binario y envia un nodo con el valor al final de la lista while( (ch=getchar())!='\n' ){ num=charInt(ch); if(num!=0 && num!=1); else{ insertarNodo(num); contador++; } } int Hamm[contador]; lista *aux; //convertir de lista a cadena for(aux=cabeza,i=0;aux!=NULL;aux=aux->sig){ Hamm[i]=aux->bit; i++; } i=0; //halla la cantidad de bits de paridad while(lonParidad<contador){ lonParidad=pow(2,i)-1; i++; } int paridad[lonParidad];
");
.
//nuevamente llama la funcion para hallar los bits de paridad int *array2=hallarBitsParidad(contador,Hamm,lonParidad,paridad); for(i=0;i<lonParidad;i++) paridad[i]=*(array2+i); printf("El error esta en la posicion\n "); for(i=lonParidad-2; i>=0 ; i--) printf(" %i ", paridad[i]); printf("\n"); }} //asignacion del array recibido }while(opcion!=3); return 0; } //FUNCIONES int longitudHam(int lonHam){ int k=0; int temp=0; while(temp<lonHam){ temp=pow(2,k); lonHam++; k++; } lonHam-=1; return lonHam; } //halla si un numero es par short esPar(int num){ int residuo=num%2; if(residuo==0) return 0; else return 1; } //pasa de caracter a entero int charInt(char caracter) { int auxiliar =0; auxiliar = caracter-48; return auxiliar; } //Inserta nodos void insertarNodo(int dato){ struct nodo *nuevo=NULL; nuevo=malloc(sizeof(struct nodo)); nuevo->sig=NULL; nuevo->bit=dato; //inserta en caso de lista vacia if(cabeza==NULL){ cabeza=malloc(sizeof(struct nodo)); cabeza->sig=NULL; cabeza->bit=dato; }else{ insertarElNodo(cabeza,nuevo); } } //inserta nodo al final de la lista void insertarElNodo(struct nodo *actual, struct nodo *nuevo){ //marca la cantidad de veces q se busca el bit de paridad y por ende posicin en el array for(distancia=1;bitParidad<lonParidad;distancia*=2){ int d=1; //ajusta la posicion inicial de cada linea contParidad=0; for(i=0; i<lonHam ; i++){ if(distancia==d){ int j; for (j=0;j<distancia && i<lonHam;j++){ contParidad+=Hamm[i]; i++; } i--; d=0; }else d++; } paridad[bitParidad]=esPar(contParidad); bitParidad++; } return paridad; } int contParidad,distancia; int bitParidad=0; } int *hallarBitsParidad(int lonHam,int * array,int lonParidad, int * paridad){ int Hamm[lonHam]; // int paridad[lonParidad]; int i; for(i=0;i<lonHam;i++) Hamm[i]=*(array+i); struct nodo *aux; for(aux=actual;aux->sig!=NULL;aux=aux->sig); aux->sig=nuevo;
.
p = p->next; } if (pred) pred->next = i; else head = i; i->next = NULL; } int showlist(lista *p) { int cont=0; while (p != NULL) { p = p->next; cont++; } return cont; } int main() { //Crea lista entrelazada y creacion de arreglo lista *aux; lista *p; char c[1]; int i=0,j=0; int num=0; int suma; int opcion; printf("Ingrese los datos \n"); do{ c[0]=getchar(); if(c[0]!='\n'){ /*if(c[0]==' '){ c[0]='22'; }*/ num=atoi(c); p = (lista *) malloc(sizeof(lista)); if(num>9){ num=num/10; } p->info = num; insertar(p); } }while(c[0]!='\n'); printf("\n"); num=showlist(head); int datos[num]; printf("Si desea codificar: \n 1 - Codificar\n 2 Decodificar\n X - Salir\n"); scanf("%i",&opcion); aux=head; for(i=0;i<num;i++){ datos[i]=aux->info; aux=aux->next; } //Tamao del arreglo int tam=sizeof(datos)/sizeof(datos[0]); if(opcion==1){ // Creacion matriz int filas, columnas; columnas=8; filas=(tam/columnas)+2; char mat[filas][columnas]; int k=0; i=0; j=0; for(i=0;i<filas-1;i++){ for(j=0;j<columnas-1;j++){ if(k<tam){ if(datos[k]==22){ mat[i][j]=' '; }else{ mat[i][j]=(char)datos[k] + 0x30;} k++; }else{ mat[i][j]=' '; } } } //Insertando Bits de paridad printf("\n"); suma=0; int sumah=0; int sumav=0; //Paridad Horizontal for(i=0;i<filas-1;i++){ suma=0; for(j=0;j<columnas-1;j++){ if(mat[i][j]=='1') suma=suma+1; } mat[i][columnas-1]=(char)(suma%2)+0x30; if(mat[i][columnas-1]=='1'){ sumah=sumah+1; } } //Paridad vertical printf("\n"); for(j=0;j<columnas;j++){ suma=0; for(i=0;i<filas-1;i++){ if(mat[i][j]=='1'){ suma=suma+1; } } mat[filas-1][j]=(char)(suma%2)+0x30; //sumav=mat[filas-1][j]+sumav; } //mat[filas-1][columnas-1]=(sumav+sumah)%2; printf("\n"); printf("%i %i %i\n",filas,columnas,tam); printf("\n"); for(i=0;i<filas;i++){ for(j=0;j<columnas;j++){ printf("%c",mat[i][j]); } printf("\n"); } }else{ if(opcion==2){ int filas, columnas; columnas=8; filas=(tam/columnas); char mat[filas][columnas]; char comp[filas][columnas]; int k=0; i=0; j=0; suma=0; for(i=0;i<filas;i++){
.
for(j=0;j<columnas;j++){ mat[i][j]=(char)datos[k]+0x30; //printf("%c %i",mat[i][j],datos[k]); //system("PAUSE"); if(j!=columnas-1&&i!=filas-1){ comp[i][j]=(char)datos[k]+0x30; } k++; } } } //Insertando Bits de paridad printf("\n"); suma=0; int sumah=0; int sumav=0; //Paridad Horizontal for(i=0;i<filas-1;i++){ suma=0; for(j=0;j<columnas-1;j++){ if(comp[i][j]=='1'){ suma=suma+1; } } comp[i][columnas-1]=(char)suma%2+0x30; if(comp[i][columnas-1]=='1'){ sumah=sumah+1; } } //Paridad vertical printf("\n"); for(j=0;j<columnas;j++){ suma=0; for(i=0;i<filas-1;i++){ if(comp[i][j]=='1'){ suma=suma+1; } } comp[filas-1][j]=(char)suma%2+0x30; } // Comparar bits de paridad for(i=0;i<filas-1;i++){ if(mat[i][columnas-1]!=comp[i][columnas1]){ printf("Error en fila; %i \n",i+1); } } for(j=0;j<columnas-1;j++){ if(mat[filas-1][j]!=comp[filas-1][j]){ printf("Error en columna; %i \n",j+1); } } printf("\n"); printf("%i %i %i\n",filas,columnas,tam); printf("\n"); for(i=0;i<filas;i++){ for(j=0;j<columnas;j++){ printf("%c",mat[i][j]); } printf("\n"); } printf("\n"); printf("%i %i %i\n",filas,columnas,tam); printf("\n"); for(i=0;i<filas;i++){ for(j=0;j<columnas;j++){ printf("%c",comp[i][j]); } printf("\n"); } } } system("PAUSE");
5. CONCLUSIONES
Se disearon 2 algoritmos capaces de detectar errores, despus de haber ingresado una cantidad ilimitada de datos. El cdigo haming diseado permite tanto codificar como decodificar palabras en binario de diferentes tamaos
para disminuir la tasa de error en una comunicacin, estos no son totalmente efectivos ya que presentan casos en los cules tienden a no tener exactitud de acuerdo a la veracidad de la informacin, pero an as permite la tendencia a una ptima comunicacin
REFERENCIAS
[1] Herramientas web para la enseanza de protocolos de comunicacin. Disponible en http://neo.lcc.uma.es/ [2] CDIGOS Y CDIGOS DE DETECCIN DE ERRORES. CAPITULO 10 Disponible en http://docencia.udea.edu.co/ [3] Introduccin a los cdigos correctores de errores. Disponible en http://personales.mundivia.es/jtoledo/angel/error/error1.htm