ANEXOS -...

143
1 ANEXOS ANEXO 1. Formulas lógicas proposicionales para SAT-FNC .............................................................................3 ANEXO 2. Conjuntos, Relaciones y Funciones .................................................................................................10 ANEXO 3. Programación Lógica: algoritmo en lenguaje C ...............................................................................27 ANEXO 4. Problemas Satisfactibilidad ...............................................................................................36 ANEXO 5. Problemas -completos .................................................................................................................38 ANEXO 6. Problemas y ............................................................................................................................41 ANEXO 7. Proposiciones y variables lógicas .....................................................................................................49 ANEXO 8. El poder de los lenguajes de programación ......................................................................................60 ANEXO 9. Lenguajes recursivamente numerables y recursivos .........................................................................77 ANEXO 10. Ordenamiento y búsqueda ............................................................................................................97 ANEXO 11. Sistemas Secuenciales Biestables ...............................................................................................108 TEOREMAS .........................................................................................................................................................132 Teorema 1. Dos conjuntos son iguales si, y solo si, cada uno es subconjunto del otro ..........................................132 Teorema 2. El conjunto vacío es subconjunto de cualquier conjunto. ..................................................................132 Teorema 3. Dado un conjunto y subconjuntos del mismo........................................................................132 Teorema 4. Sea un conjunto y subconjuntos arbitrarios de el. ..............................................................132 Teorema 5. La relación inversa de una equivalencia es ella misma. ......................................................................133 Teorema 6. Sea una equivalencia definida en un conjunto entonces cada elemento del conjunto está en la clase que representa. ...............................................................................................................................................133 Teorema 7. Si es una equivalencia en el conjunto , sus clases de equivalencia constituyen una partición de . ................................................................................................................................................................................133 Teorema 8. Dada una partición de un conjunto, existe una equivalencia definida en dicho conjunto cuyas clases de equivalencia son los subconjuntos que constituyen la partición. ...........................................................................134 Teorema 9. La relación inversa de un orden es también un orden, denominado orden inverso. ............................134 Teorema 10. Todo elemento máximo es maximal y, si existe, el máximo es único. .............................................134 Teorema 11. Un subconjunto acotado superiormente tiene máximo si, y solo si, tiene supremo y este pertenece a dicho subconjunto. ..................................................................................................................................................134 Teorema 12. En un orden total todo maximal es máximo y, por tanto, único y todo minimal es mínimo y, por tanto, único. ............................................................................................................................................................134 Teorema 13. En un conjunto con más de un elemento, si un orden total es lineal, entonces no verifica las propiedades del inmediato sucesor ni del inmediato antecesor. .............................................................................135 Teorema 14. Un orden total verifica la propiedad del supremo si, y solo si, verifica la propiedad del ínfimo. .....135 Teorema 15. Ordenación por comparación ............................................................................................................135 Teorema 16. no es un lenguaje recursivamente enumerable. ...........................................................................135

Transcript of ANEXOS -...

1

ANEXOS

ANEXO 1. Formulas lógicas proposicionales para SAT-FNC ............................................................................. 3

ANEXO 2. Conjuntos, Relaciones y Funciones .................................................................................................10

ANEXO 3. Programación Lógica: algoritmo en lenguaje C ...............................................................................27

ANEXO 4. Problemas Satisfactibilidad ...............................................................................................36

ANEXO 5. Problemas -completos .................................................................................................................38

ANEXO 6. Problemas y ............................................................................................................................41

ANEXO 7. Proposiciones y variables lógicas .....................................................................................................49

ANEXO 8. El poder de los lenguajes de programación ......................................................................................60

ANEXO 9. Lenguajes recursivamente numerables y recursivos .........................................................................77

ANEXO 10. Ordenamiento y búsqueda ............................................................................................................97

ANEXO 11. Sistemas Secuenciales Biestables ...............................................................................................108

TEOREMAS .........................................................................................................................................................132

Teorema 1. Dos conjuntos son iguales si, y solo si, cada uno es subconjunto del otro ..........................................132

Teorema 2. El conjunto vacío es subconjunto de cualquier conjunto. ..................................................................132

Teorema 3. Dado un conjunto y subconjuntos del mismo ........................................................................132

Teorema 4. Sea un conjunto y subconjuntos arbitrarios de el. ..............................................................132

Teorema 5. La relación inversa de una equivalencia es ella misma. ......................................................................133

Teorema 6. Sea una equivalencia definida en un conjunto entonces cada elemento del conjunto está en la

clase que representa. ...............................................................................................................................................133

Teorema 7. Si es una equivalencia en el conjunto , sus clases de equivalencia constituyen una partición de .

................................................................................................................................................................................133

Teorema 8. Dada una partición de un conjunto, existe una equivalencia definida en dicho conjunto cuyas clases de

equivalencia son los subconjuntos que constituyen la partición. ...........................................................................134

Teorema 9. La relación inversa de un orden es también un orden, denominado orden inverso. ............................134

Teorema 10. Todo elemento máximo es maximal y, si existe, el máximo es único. .............................................134

Teorema 11. Un subconjunto acotado superiormente tiene máximo si, y solo si, tiene supremo y este pertenece a

dicho subconjunto. ..................................................................................................................................................134

Teorema 12. En un orden total todo maximal es máximo y, por tanto, único y todo minimal es mínimo y, por

tanto, único. ............................................................................................................................................................134

Teorema 13. En un conjunto con más de un elemento, si un orden total es lineal, entonces no verifica las

propiedades del inmediato sucesor ni del inmediato antecesor. .............................................................................135

Teorema 14. Un orden total verifica la propiedad del supremo si, y solo si, verifica la propiedad del ínfimo. .....135

Teorema 15. Ordenación por comparación ............................................................................................................135

Teorema 16. no es un lenguaje recursivamente enumerable. ...........................................................................135

2

Teorema 17. Si es un lenguaje recursivo, entonces también lo es. ..................................................................135

Teorema 18. Si existe una reducción de a ...................................................................................................136

Teorema 19. Las implicaciones directa y contrapositiva son equivalentes, y las implicaciones inversa y reciproca

son equivalentes. .....................................................................................................................................................136

Teorema 20. La doble implicación es equivalente a la conjunción de las implicaciones directa e inversa............137

Teorema 21. La implicación de dos proposiciones es equivalente a la disyunción de la negación de la primera con

la segunda. ..............................................................................................................................................................137

Teorema 22. La negación de la negación es equivalente a la proposición original. ...............................................137

Teorema 23. Conjunción de proposiciones satisface las propiedades de idempotencia, asociatividad,

conmutatividad, existencia de un elemento neutro y de un elemento dominante ...................................................138

Teorema 24. La disyunción de proposiciones satisface las propiedades de idempotencia, asociatividad,

conmutatividad, existencia de un elemento neutro y de un elemento dominante. ..................................................138

Teorema 25. Las siguientes relaciones son validas para cualesquiera proposiciones ..................................139

Teorema 26. Si es un enunciado abierto, con una variable, entonces se cumplen las equivalencias .........140

Teorema 27. Si es un enunciado abierto que depende de dos variables, se cumplen las siguientes

equivalencias entre proposiciones. .........................................................................................................................140

Teorema 28. Para proposiciones cualesquiera los siguientes son razonamientos lógicos ........................140

GLOSARIO...........................................................................................................................................................142

3

ANEXO 1. Formulas lógicas proposicionales para SAT-FNC

Materiales

Equipos

Mano de obra

{

4

Materiales

Equipos

Mano de obra

{

5

Materiales

Equipos

Mano de obra

{

6

Materiales

Equipos

Mano de obra

{

7

Materiales

Equipos

Mano de obra

{

8

Materiales

Equipos

Mano de obra

9

Materiales

Equipos

Mano de obra

{

10

Materiales

Equipos

Mano de obra

{

ANEXO 2. Conjuntos, Relaciones y Funciones

11

p1

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┬ ┬ ┬

┬ ┴ ┴

┴ ┬ ┴

p1

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

1 1 1

1 0 0

0 1 0

p1

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

r 1 r 2

r 3 r 4

c11

c12

c13

c21

c22

c23

c31

c32

c33

1 1 0 0 0 0 0 0

1 1

1 1

1 1

1

0 0 0

0 0 0 0 0 0

0 0 0

0 0 0 0 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 00 0 0

1

10

1

1 10

0 1

0

p1

11

12

13

21

22

23

31

32

33

c11 c12 c13

c21

c32

r 1r 2

r 3

r 4

12

p2

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┬ ┴ ┴

┬ ┬ ┬

┴ ┬ ┴

p2

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

1 0 0

1 1 1

0 1 0

p2

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

r 1

r 2 r 3

r 4

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 0

1 10 0 0 0 0 0

1

10

p2

1 1 1

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 00 0 0

11

12

13

21

22

23

31

32

33

c11

c21c22 c23

c32

r 1

r 2

r 3

r 4

13

14

p3

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┴ ┬ ┴

┬ ┴ ┴

┬ ┬ ┬

p3

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

0 1 0

1 0 0

1 1 1

p3

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

r 1

r 2

r 3

r 4

c11

c12

c13

c21

c22

c23

c31

c32

c33

p3

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 10 0 0 0 0 010

0 1 1 0 0 0 0 0 01

1 1 10 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

11

12

13

21

22

23

31

32

33

c21

c12

c31 c32 c33

15

p4

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┬ ┬ ┴

┬ ┬ ┴

┴ ┬ ┬

p4

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

1 1 0

1 1 0

0 1 1

p4

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

r 1

r 2

r 3

r 4

r 5

r 6

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

p4

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 10 0 0 0 0 010

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

11

12

13

21

22

23

31

32

33

c11 c12

c21 c22

c32 c33

r 1

r 2

r 3

r 4

r 5

r 6

16

17

p5

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┴ ┬ ┴

┬ ┬ ┬

┬ ┬ ┴

p5

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

0 1 0

1 1 1

1 1 0

p5

M

c11 c12 c13

c21 c22 c23

c31 c32 c33r 1

r 2

r 3

r 4

r 5

r 6

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

0 0 0 0 0 00 0 0

p5

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 10 0 0 0 0 010

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0

12

21

22

23

31

32

12

13

23

c12

c21 c22 c23

c31 c32

r 1

r 6

r 2

r 3

r 4

r 5

18

19

p6

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┬ ┴ ┴

┬ ┬ ┴

┬ ┬ ┬

p6

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

1 0 0

1 1 0

1 1 1

p6

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

r 1

r 2

r 3

r 4

r 5

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

0 0 0 0 0 0 00 0 0

p6

0 1 1 0 0 0 0 0 01

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

11

12

13

21

22

23

31

32

33

c11

c21 c22

c31 c32 c33

r 1

r 2

r 3

r 4

r 5

20

21

p7

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┴ ┬ ┬

┴ ┬ ┴

┬ ┬ ┴

p7

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

0 1 1

0 1 0

1 1 0

p7

M

c11 c12 c13

c21 c22 c23

c31 c32 c33r 1

r 2

r 3

r 4

r 5

r 6

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

0 0 0 0 0 0 00 0 0

1 10 0 0 0 0 010

1 10 0 0 0 0 010

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

p7

11

12

13

21

22

23

31

32

33

c31 c32

c22

c12

c13

r 1

r 2

r 3

r 6

r 5

r 4

22

23

p8

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┴ ┬ ┴

┴ ┬ ┴

┬ ┬ ┬

p8

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

0 1 0

0 1 0

1 1 1

p8

M

c11 c12 c13

c21 c22 c23

c31 c32 c33r 1

r 2

r 3 r 4

r 5

r 6

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

0 0 0 0 0 0 00 0 0

p8

1 10 0 0 0 0 010

1 10 0 0 0 0 010

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

0 0 0 0 0 0 00 0 0

11

12

13

21

22

23

31

32

33

c12

c22

c32c31

c33

r 1

r 2

r 3

r 4

r 5

r 6

24

p9

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┴ ┴ ┬

┬ ┬ ┬

┴ ┬ ┬

p9

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

0 0 1

1 1 1

0 1 1

p9

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

r 5

r 1

r 2

r 3 r 4

r 6

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

0 0 0 0 0 0 00 0 0

p9

1 10 0 0 0 0 010

0 0 0 0 0

0 0 0

0 0

0 0 0 0 0

0 0 0

0 0

0 0

0 0 0

1 1 10 0 00 0 0 000 0 0

10 0 0 0 0 0 00 0 0 0 0 0

0 0 0 0 0 0 00 0 0 0 0 0 0 0

0 0 0 0 0 0 00 0 0 0 0 0 0 0

0

1

11

12

13

21

22

23

31

32

33

c13

c23

c33

c22

c32

c21

r 1

r 2

r 3

r 4

r 5

r 6

25

26

p10

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

┴ ┬ 1

┴ ┬ ┬

┬ ┬ ┬

p10

M

c11 c12 c13

c21 c22 c23

c31 c32 c33

0 1 1

0 1 1

1 1 1

p10

M

c11 c12 c13

c21 c22 c23

c31 c32 c33r 1

r 2

r 3

r 4

r 5

r 6

r 7

r 8

p10

c11

c12

c13

c21

c22

c23

c31

c32

c33

0 1 1 0 0 0 0 0 01

1 10 0 0 0 0 010

1 1 10 0 0 00 0 0

0 0 0 0 0 0 00 0 0

1 10 0 0 0 0 010

0 0 0

0

0 0

0 0 0

0

0 0

0 0

0

1 1 10 0 00 0 000 0 0

1 10 0 0 0 0 010 00 0

1 1 10 0 0 00 0 0 0 0 0

0 0 0 0 0 0 00 0 0 0 0 0

1

1

12

13

21

22

23

31

32

33

c31c32

c22

c12 c13

c23

c33

r 1

r 2

r 3

r 4

r 5

r 6

r 8

r 7

27

ANEXO 3. Programación Lógica: algoritmo en lenguaje C

/* * File: main.c * Author: mrincon * * Created on June 15, 2016, 2:55 PM */ #include <stdio.h> #include <stdlib.h> #include <conio.h> #include <math.h> #include <errno.h> #include <time.h> #define L 15 //Recurso Labor(ManoObra) #define E 15 //Recurso Equip(Maquina) #define C 8 //Dimension MUX81 #define M 15 //Recurso Inv(Materiales) #define T 200 //Tiempo 480 min/dia #define D 2 //Tiempo dias #define P 10 //Cant Prod #define W 8 //Cant WC #define X 1050 //Dimension Filas Tabla Verdad #define Y 11 //Dimension Columna Tabla Verdad. # Variables max int MUX81(int MUXi[], int z); void main(){ int xx,c1,c2,c3,SelP,SelW,t1,t2,t3,z1,z2,sumP[P],sumWP[W][P],mat[M],equ[E],lab[L],In[M],Eq[E],La[L]; int s0,s1,s2,s3,s4,s5,s6,s7,s8,s9,s10,s11,s12,s13; int SOc[P],SOi[P],SOt[P],SOe[P],WCrPc[W][P],WCiPi[W][P],WCtPt[W][P],WCePe[W][P],WCe[W],WCt[W],WCr[W],WCb[W]; int p0,p1,p2,p3,p4,p5,p6; int *ip; double random(); FILE *infile; //p1=1;p2=1;p3=1;p4=1; printf("\n\tPRODUCTION SCHEDULE\n"); /* printf("Print SOi [0,1] "); scanf("%d",&p0); printf("Print SOt [0,1] "); scanf("%d",&p1); printf("Print SOe [0,1] "); scanf("%d",&p2); */ p1=p2=p3=0; printf("Print WCi [0,1] "); scanf("%d",&p3); printf("Print WCt [0,1] "); scanf("%d",&p4); printf("Print WCe [0,1] "); scanf("%d",&p5); if((infile=fopen("C:/temp/inv.txt","rt"))==NULL) exit(0); for(c1=1;c1<=M;c1++) fscanf(infile,"%d",&In[c1]); //Inventario Disponibilidad (t) fclose(infile); if((infile=fopen("C:/temp/equ.txt","rt"))==NULL) exit(0); for(c1=1;c1<=E;c1++) fscanf(infile,"%d",&Eq[c1]); //CRP Disponibilidad (t) seg/dia fclose(infile);

28

if((infile=fopen("C:/temp/lab.txt","rt"))==NULL) exit(0); for(c1=1;c1<=L;c1++) fscanf(infile,"%d",&La[c1]); //CRP Disponibilidad (t) seg/dia fclose(infile); /* Sistema Logico Combinacional por c/u WC */ t1=1; do{ if((infile=fopen("C:/temp/SOc.txt","rt"))==NULL) exit(0); c1=0; while(!feof(infile)){ fscanf(infile,"%d",&SOc[c1]); //Cant.(OS/WO) Setup MPS if(SOc[c1]>0) SOt[c1]=SOi[c1]=1; else SOt[c1]=SOi[c1]=0; //printf("\nSOi=%d\t\tSOt[%d]=%d",SOi[c1],c1,SOt[c1]); sumP[c1]=0; //printf(" %d",SOc[c1]); c1++; } fclose(infile); z1=c1-1; //printf("\n%d",z1); if((infile=fopen("C:/temp/WCr.txt","rt"))==NULL) exit(0); c2=0; while(!feof(infile)){ fscanf(infile,"%d",&WCr[c2]); //Cant.(OS/WO) Setup MPS //printf("\ntWCr[%d]=%d",c2,WCr[c2]); c2++; } fclose(infile); z2=c2-1; //printf("\n%d",z2); if((infile=fopen("C:/temp/WCiPi.txt","rt"))==NULL) exit(0); while(!feof(infile)){ for(c2=0;c2<=z2;c2++){ //Cant.WCi2 for(c1=0;c1<=z1;c1++){ //Cant.Pi fscanf(infile,"%d",&WCiPi[c2][c1]); //Relacion.(WCi/Pi) Setup CRP. !!MRP?!! WCtPt[c2][c1]=WCiPi[c2][c1]; WCrPc[c2][c1]=WCr[c2]*SOc[c1]*WCiPi[c2][c1]; WCePe[c2][c1]=sumWP[c2][c1]=0; //printf("[%d][%d] %d\n",c2,c1,WCtPt[c2][c1]); //printf("%d\t",WCrPc[c2][c1]); } WCe[c2]=0; //printf("%d %d %d| ",z2,c2,WCe[c2]); //printf("\n"); } } fclose(infile); t3=0; for(t2=1;t2<=T;t2++){ for(c1=1;c1<M;c1++){ mat[c1]=1;//random();

29

equ[c1]=1;//random(); lab[c1]=1;//random(); } //Centro de trabajo C11 s0=(mat[1]&&mat[2]); s1=(mat[3]&&mat[4]); s2=(mat[5]&&mat[6]); s3=(s0&&s1); s4=(s3&&s2); s5=(mat[5]&&mat[6]&&equ[1]&&lab[1]); s6=(equ[2]||equ[3]); s9=(lab[1]||lab[2]); s7=(s0&&s1&&s5&&s6&&s9); s10=(s9||lab[3]); s8=(s2&&s3&&s7&&equ[3]&&s10); WCb[0]=(s4&&s8&&s10); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[0],s4,s8,s10); //Centro de trabajo C21 s0=(mat[1]&&mat[2]); s1=(mat[3]&&mat[4]); s2=(mat[5]&&mat[6]); s3=(mat[7]&&mat[8]); s4=(s0&&s1); s5=(s2&&s3); s6=(s4&&s5); s7=(mat[5]&&mat[6]&&equ[1]&&lab[1]); s8=(mat[7]&&mat[8]&&equ[3]&&lab[2]); s11=(lab[1]||lab[2]); s12=(s11||lab[3]); s9=(equ[2]&&s0&&s1&&s7&&s8&&s11); s10=(equ[4]&&s4&&s5&&s9&&s12); WCb[1]=(s6&&s10&&s12); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[1],s6,s10,s12); //Centro de trabajo C31 s0=(mat[1]&&mat[2]); s1=(mat[3]&&mat[4]); s2=(s0&&s1); s3=(s2&&mat[5]); s7=(lab[1]||lab[3]); s8=(s7||lab[2]); s9=(s8||lab[3]); s4=(mat[1]&&mat[2]&&s1&&equ[1]&&s7); s5=(equ[2]&&s0&&s1&&s4); s6=(equ[3]&&s2&&s5&&s9); WCb[2]=(s3&&s6&&s9); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[2],s3,s6,s9); //Centro de trabajo C12 s0=(mat[1]&&mat[2]&&mat[3]); s1=(mat[4]&&mat[5]&&mat[6]); s2=(s0&&s1); s6=(lab[1]||lab[2]); s7=(s6||lab[3]); s3=(lab[1]&&s1&&equ[1]); s4=(equ[2]&&s0&&s3&&s6); s5=(equ[3]&&s2&&s4&&s7); WCb[3]=(s2&&s5&&s7); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[3],s2,s5,s7); //Centro de trabajo C22 s0=(mat[1]&&mat[2]); s1=(mat[5]&&mat[6]); s2=(s0&&s1&&mat[3]&&mat[4]); s6=(lab[1]||lab[2]); s7=(lab[3]||lab[4]); s8=(s6||s7);

30

s3=(equ[1]&&mat[5]&&mat[6]&&s1&&s6); s4=(equ[2]&&s0&&s3&&s7); s5=(equ[3]&&s2&&s4&&s8); WCb[4]=(s3&&s6&&s9); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[4],s3,s6,s9); //Centro de trabajo C32 s0=(mat[1]&&mat[2]&&mat[3]&&mat[4]&&mat[5]); s4=(lab[1]||lab[2]||lab[3]); s1=(equ[1]&&s0&&s4); s2=(equ[2]&&s0&&s4); s3=(s1&&s2); WCb[5]=(s3&&s6&&s9); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[5],s3,s6,s9); //Centro de trabajo C13 s0=(mat[1]&&mat[2]); s1=(mat[4]&&mat[5]&&mat[6]); s2=(s0&&s1); s3=(s2&&s1); s8=(lab[2]||lab[3]); s9=(s8||lab[3]); s4=(equ[1]&&lab[2]&&s1); s5=(equ[3]&&lab[1]&&s0); s6=(equ[2]&&s2&&s4&&s5&&s8); s7=(equ[4]&&s3&&s6&&s9); WCb[6]=(s3&&s7&&s9); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[6],s3,s7,s9); //Centro de trabajo C23 s0=(mat[1]&&mat[2]); s1=(mat[3]&&mat[4]); s2=(mat[5]&&mat[6]); s3=(mat[7]&&mat[8]); s4=(s0&&s1); s5=(s2&&s3); s6=(s4&&s5); s10=(lab[1]||lab[3]); s11=(lab[2]||s10); s12=(lab[3]||s11); s7=(equ[1]&&mat[7]&&mat[8]&&s10); s8=(equ[2]&&s1&&s7&&s11); s9=(equ[3]&&s4&&s5&&s8&&s12); WCb[7]=(s6&&s9&&s12); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[7],s6,s9,s12); //Centro de trabajo C33 s0=(mat[1]&&mat[2]); s1=(mat[4]&&mat[5]&&mat[6]); s2=(s0&&s1); s3=(s2&&s1); s8=(lab[2]||lab[3]); s9=(s8||lab[3]); s4=(equ[1]&&lab[2]&&s1); s5=(equ[3]&&lab[1]&&s0); s6=(equ[2]&&s2&&s4&&s5&&s8); s7=(equ[4]&&s3&&s6&&s9); WCb[8]=(s3&&s7&&s9); //printf("\n<%d> WC.Bool \t%d\t%d\t%d\t%d",WCt[7],s3,s7,s9); c1=0; do{ SelP=MUX81(SOt,z1); //Select Product de SOt en MUX81. MT Nivel I c2=0; do{ for(c3=0;c3<=z2;c3++){ WCt[c3]=WCtPt[c3][c1]; //printf("%d\t",WCtPt[c3][SelP]);

31

} //printf("\n"); SelW=MUX81(WCt,z2); //Select Centro Trabajo de WCi en MUX81. MT Nivel II if(((WCtPt[c2][c1]==1)&&(c2==SelW))){ if(!(WCePe[c2][c1]^WCe[c2])){ WCe[c2]=WCePe[c2][c1]=1; sumWP[c2][c1]+=WCePe[c2][c1]; if(sumWP[c2][c1]>WCrPc[c2][c1]){ WCe[c2]=WCtPt[c2][c1]=WCePe[c2][c1]=0; sumWP[c2][c1]--; //WCrPc[c2][c1]-=sumWP[c2][c1]; } } } else{ WCePe[c2][c1]=0; } c2++; }while(c2<=z2); //WCe[c2]=(WCe[c2]||WCtPt[c2][c1]); /* for(c2=0;c2<=z2;c2++){ for(c1=0;c1<=z1;c1++){ WCe[c2]=(WCe[c2]||WCtPt[c2][c1]); //printf("%d\t",WCtPt[c2][c1]); } } */ //if((SOi[c1]||SOt[c1])==1){ /* if(SOt[c1]==1){ SOe[c1]=1; //SOi[c1]=0; sumP[c1]+=SOe[c1]; if(sumP[c1]>SOc[c1]){ // SOt[c1]=SOe[c1]=0; sumP[c1]--; //SOc[c1]-=sumP[c1]; } } else SOe[c1]=0; */ c1++; }while(c1<=z1); printf("\n<%d> %d\t",t1,t2); /* printf("\t"); for(c1=0;c1<=z1;c1++) printf("%d ",SOc[c1]); */ if(p0==1){ printf("\t"); for(c1=0;c1<=z1;c1++){ if(SOi[c1]==1) printf("%d ",SOi[c1]); else printf("%d ",SOi[c1]); } } if(p1==1){ printf("\t");

32

for(c1=0;c1<=z1;c1++){ if(SOt[c1]==1) printf("%d ",SOt[c1]); else printf("%d ",SOt[c1]); } } if(p2==1){ printf("\t"); for(c1=0;c1<=z1;c1++){ if(SOe[c1]==1) printf("%d ",SOe[c1]); else printf("%d ",SOe[c1]); } } /* printf("\t"); for(c1=0;c1<=z1;c1++) printf("%d ",sumP[c1]); printf("\t"); for(c2=0;c2<=z2;c2++) printf("%d\t",WCr[c1]); */ if(p3==1){ printf("\n"); for(c1=0;c1<=z1;c1++){ printf("\t"); for(c2=0;c2<=z2;c2++){ if(WCiPi[c2][c1]==1) printf("%d",WCiPi[c2][c1]); else printf("%d",WCiPi[c2][c1]); } } } if(p3==1){ printf("\n"); for(c1=0;c1<=z1;c1++){ printf("\t"); for(c2=0;c2<=z2;c2++){ if(WCtPt[c2][c1]==1) printf("%d",WCtPt[c2][c1]); else printf(" "); } } } if(p4==1){ //printf("\n"); for(c1=0;c1<=z1;c1++){ printf("\t"); for(c2=0;c2<=z2;c2++){ if(WCePe[c2][c1]==1) printf("%d ",WCePe[c2][c1]); else printf(" "); } } } if(p5==1){ //printf("\n"); //for(c1=0;c1<=z1;c1++){ printf("\t");

33

for(c2=0;c2<=z2;c2++){ if(WCe[c2]==1) printf("%d ",c2); else printf(" "); } //} } /* printf("\t"); for(c2=0;c2<=z2;c2++) printf("%d\t",sumW[c2]); */ //getch(); } //getch(); t1++; }while(t1<D); } int _seed1=1000,_seed2=12000,_seed3=28000; double random() { double r; int s; _seed1=(_seed1%177)*171-(_seed1/177)*2; if(_seed1<0)_seed1+=30269; _seed2=(_seed2%176)*172-(_seed2/176)*35; if(_seed2<0)_seed2+=30307; _seed3=(_seed3%178)*170-(_seed3/178)*63; if(_seed3<0)_seed3+=30323; r=_seed1/30269.0+_seed2/30307.0+_seed3/30323.0; while(r>1.0) r-=1.0; if(r<=0.5) s=0; else s=1; return s; } double bool(p) double p; { /* Random Booleano Generador de Numeros Pseudoaleatorios de 0 y 1 */ int c,i0,i1,j0,j1,k0,k1,v0,bool[X][Y]; FILE *fp; i1=p; //Cant.Variables j1=pow(2.0,p); //Cant.Combinaciones k1=(j1/2); //Frecuencia por Variable - Tabla de Verdad c=(i1*j1)/2; //Cant.(c/u) - Ceros y Unos /* printf("\nCant.Combinaciones\t%d\nFrec.Variable (2n/2)\t%d\nCant.Binaria\t%d\n",j1,k1,c); getch(); */ for(i0=1;i0<=i1;i0++){ //printf("\nVar %d",i0); k1=(pow(2.0,i0)/2); k0=1; for(j0=1;j0<=j1;j0++){ //printf("\n<%d>",j0); if(k0<=k1){ v0=0;

34

k0++; } else{ if((k0>k1)&&(k0<=(2*k1))){ v0=1; k0++; } } if(k0>(2*k1)) k0=1; bool[j0][i0]=v0; //printf("\tj%d i%d\t%d",j0,i0,bool[j0][i0]); //getch(); } } fp = fopen("C:/temp/test.txt","w+"); for(j0=1;j0<=j1;j0++){ //fprintf(fp,"<%d>",j0); for(i0=1;i0<=i1;i0++){ fprintf(fp,"%d\t",bool[j0][i0]); } fprintf(fp,"\n"); } fclose(fp); } int MUX81(int MUXi[C], int z){ int i,j,x,e,m1,m2,MUXs[C][3],iMUX[C]; int I,F,s0,s1,s2,i0,i1,i2,i3,i4,i5,i6,i7; double q; FILE *fw; q=3; //q Cant bits bool(q); //Llama a la funcion bool() if((fw=fopen("C:/temp/test.txt","rt"))==NULL) //Tabla de verdad - Selecccionador s0,s1,s2 MUX41 exit(0); for(i=0;i<C;i++){ for(j=0;j<3;j++){ fscanf(fw,"%d",&MUXs[i][j]); } } fclose(fw); /* for(m1=0;m1<=z;m1++) printf("\n<%d>MUX wo.wc\t%d",m1,MUXi[m1]); //Valores SOt / WOt printf("\nInhibir? 0/1 "); scanf("%d",&e); */ e=0; x=0; for(i=0;i<C;i++){ I=!e; s0=MUXs[i][0]; s1=MUXs[i][1]; s2=MUXs[i][2]; //printf("\n<%d> %d\t\t%d\t%d\t%d\t\t",i,I,s0,s1,s2); //Out s0,s1,s2 Select iMUX[0]=(MUXi[0]&&I&&(!s0)&&(!s1)&&(!s2)); iMUX[1]=(MUXi[1]&&I&&s0&&(!s1)&&(!s2)); iMUX[2]=(MUXi[2]&&I&&(!s0)&&s1&&(!s2)); iMUX[3]=(MUXi[3]&&I&&s0&&s1&&(!s2)); iMUX[4]=(MUXi[4]&&I&&(!s0)&&(!s1)&&s2); iMUX[5]=(MUXi[5]&&I&&s0&&(!s1)&&s2); iMUX[6]=(MUXi[6]&&I&&(!s0)&&s1&&s2);

35

iMUX[7]=(MUXi[7]&&I&&s0&&s1&&s2); F=0; for(j=0;j<C;j++){ F=F||iMUX[j]; //printf("\t%d",iMUX[j]); } //printf("\t\tMUX.wo %d",F); //Out F del MUX81 if(iMUX[i]==1){ //iMUX[i]=0; x=i; //i=C; break; } //getch(); } return x; }

36

ANEXO 4. Problemas Satisfactibilidad

Definición. es la abreviatura satisfactibilidad, refiriéndose al problema de la lógica proposicional que así se llama y que

consiste en determinar los valores de verdad de los literales de una forma normal conjuntiva , donde

se denomina una clausula y es una disyunción de literales . Cada literal es también conocido como una proposición y

la forma en que se encuentra se dice que es una forma normal conjuntiva o . Dado que se pudiera plantear un

problema similar en lógica de predicados o en otra lógica, el problema anterior se llama problema de satisfactibilidad de

lógica proposicional, sin embargo, a menos que se especifique otra cosa, cuando se dice se entiende que se trata del

problema de lógica proposicional y no de otro. [1]

El problema se trata de un problema donde se pretende determinar si existe una interpretación que satisface una

expresión booleana o proposicional con variables y sin cuantificadores. En otras palabras, se establece si las variables de una

formula booleana dada pueden ser asignadas de una manera tal como para hacer que la formula se evalúa como verdaderas

. Si no existen tales asignaciones, la función expresada por la formula es idéntica a falsa para todas las posibles

asignaciones de variables. En este último caso, se denomina insatisfacible, de lo contrario satisfacible.

Una instancia de sería el saber si existen valores para tales que la expresión:

es cierta.

Por el contrario, el problema de si la expresión en cuestión adquiere valor falso para todas las combinaciones de sus variables,

se denomina

Mientras que la pertenencia del problema o de satisfacibilidad booleana a la clase de los -completos fue demostrada

utilizando mecanismos particulares, las pertenencias de los 21 problemas siguientes fueron demostradas mediante

reducciones polinomiales. Así, el problema se redujo polinomialmente a los problemas 0-1 INTEGER

PROGRAMMING, CLIQUE y 3- , y estos a su vez se redujeron a otros varios. La lista completa es la que se muestra

en el anexo 1. Las sangrías denotan el hecho que la -completitud del problema fue demostrada por reducción polinomial

del problema en el nivel directamente superior. Note que los nombres de los problemas están escritos con letras mayúsculas y

corresponden a abreviaciones del nombre en inglés, como es lo usual; junto a ellos, entre paréntesis, se escribe la traducción

del nombre en español.

El problema parece ser más difícil satisfactibilidad ( -completo) si permitimos que los cuantificadores "para todos

" y "existencial ", que enlace las variables booleanas. Si se utiliza sólo cuantificadores, este sigue siendo el problema SAT.

Si permitimos que sólo los cuantificadores se convierte en el problema de la tautología: -completo. Si dejamos que

ellos, el problema se llama el problema de la fórmula booleana cuantificados (QBF), que puede se ha demostrado

completa. Se cree ampliamente que los problemas son PSPACE completa-es son más difíciles que cualquier problema en NP,

aunque esto aún no ha sido demostrada. . El problema de la máxima satisfactibilidad, una generalización de , para pedir

el número máximo de cláusulas que pueden ser satisfechas por ninguna asignación. Este problema tiene aproximación de con

algoritmos eficientes, sino que es -difícil de resolver con precisión. Peor aún, el problema es -completo, lo que

significa que no hay ningún sistema de aproximación polinomial de tiempo a este problema a menos que .

37

(Problema de satisfacibilidad booleana, para fórmulas en forma normal conjuntiva)

INTEGER PROGRAMMING (Problema de la programación lineal entera)

CLIQUE (Problema del clique, véase también Problema del conjunto independiente)

SET PACKING (Problema del empaquetamiento de conjuntos)

VERTEX COVER (Problema de la cobertura de vértices)

SET COVERING (Problema del conjunto de cobertura)

FEEDBACK NODE SET

FEEDBACK ARC SET

DIRECTED HAMILTONIAN CIRCUIT (Problema del sistema hamiltoniano dirigido)

o UNDIRECTED HAMILTONIAN CIRCUIT (Problema del sistema hamiltoniano no dirigido)

3- (Problema de satisfacibilidad booleana de 3 variables por cláusula)

CHROMATIC NUMBER (Problema de la coloración de grafos)

CLIQUE COVER (Problema de la cobertura de cliques)

EXACT COVER (Problema de la cobertura exacta)

HITTING SET

STEINER TREE

3-DIMENSIONAL MATCHING (Problema del matching tridimensional)

KNAPSACK (Problema de la mochila)

JOB SEQUENCING (Problema de las secuencias de trabajo en programación de

operaciones)

PARTITION (Problema de la partición)

o MAX-CUT (Problema del corte máximo)

38

ANEXO 5. Problemas -completos

Usamos el término -completo para describir los problemas de decisión más difíciles en en el sentido de que, si

existiera un algoritmo polinómicamente acotado para un problema -completo, existiría un algoritmo polinómicamente

acotado para todos los problemas en .

Algunos de los problemas que se describen, podrían parecer más fáciles que otros y, de hecho, las complejidades de peor

caso de los algoritmos que se han ideado para resolverlos sí difieren (son funciones de crecimiento rápido como

etc.) pero, lo cual es sorprendente, todos son equivalentes en el sentido de que, si cualquiera está en

, todos lo están. Todos son -completos.

Reducciones polinómicas. La definición formal de “ -completo” emplea reducciones, o transformaciones, de un

problema a otro. Supóngase que nos interesa resolver un problema y ya tenemos un algoritmo para otro problema .

Supóngase que también tenemos una función que toma una entrada para y produce una entrada para tal que

la respuesta correcta para con x es sí si y sólo si la respuesta correcta para con es sí. Entonces, componiendo y

el algoritmo para resolver , tendremos un algoritmo para resolver .

Reducción polinómica y reducibilidad. Sea una función que establece una correspondencia entre el conjunto de

entrada de un problema de decisión y el conjunto de entrada de un problema de decisión es una reducción

polinómica (también llamada transformación polinómica) de a si se cumplen todas las condiciones siguientes:

1. se puede calcular en tiempo polinómicamente acotado.

2. Para toda cadena , si es una entrada de sí para es una entrada de sí para .

3. Para toda cadena , si es una entrada de no para es una entrada de no para .

Por lo regular es más fácil demostrar la contrapositiva.

3’. Para toda , si es una entrada de sí para es una entrada de sí para .

El problema es polinómicamente reducible (o polinómicamente transformable) a si existe una transformación

polinómica de a . (En este apartado por lo regular diremos sólo que se puede reducir a ; la cota polinómica se

sobreentiende.) Usamos la notación

para indicar que se puede reducir a .

Cabe señalar que las partes de la definición de reducción se combinan para decir que tiene la misma

respuesta para el problema que tiene para , para toda

El meollo de la reducibilidad de a es que es por lo menos tan “difícil” de resolver como . El teorema que sigue

plantea esto con mayor precisión.

Si está en , entonces está en . Sea una cota polinómica para el cálculo de , y sea una cota

polinómica para un algoritmo que resuelve . Sea una entrada de tamaño para . Entonces el tamaño de no es

mayor que (puesto que, en el peor de los casos, un programa para efectuar escribe un símbolo en cada paso). Si se

proporciona al algoritmo para resolver , dicho algoritmo ejecuta cuando más pasos. Así pues, la cantidad

39

total de trabajo efectuada para transformar en y luego usar el algoritmo que resuelve para obtener la respuesta

correcta de con es , un polinomio en

Ya podemos dar la definición formal de completo.

-difícil y -completo. Un problema es -difícil si todo problema en se puede reducir a ; es decir,

. Un problema es -completo si está en y es -difícil. Es importante darse cuenta de que “ -difícil”

no significa “en y difícil”; significa “al menos tan difícil como cualquier problema en ”. Así, un problema puede ser

-difícil y no estar en .

Ser -difícil constituye una cota inferior para el problema. Estar en constituye una cota superior. Así pues, la clase

de los problemas -completos está acotada tanto por abajo como por arriba, aunque el estado actual del conocimiento

humano no permite definir de forma nítida ninguna de esas fronteras. El teorema que sigue es consecuencia directa de la

definición y del teorema.

Si cualquier problema -completo está en , entonces Este teorema indica, por una parte, lo valioso que sería

hallar un algoritmo polinómicamente acotado para cualquier problema -completo y, por la otra, lo poco probable que

es la existencia de tal algoritmo, en vista de la gran cantidad de problemas en para los que se han buscado

infructuosamente algoritmos polinómicamente acotados.

Aunque hemos visto que muchos problemas están en , no es de ninguna manera evidente que cualquiera de ellos sea

-completo. Después de todo, para demostrar que algún problema es -difícil, lo cual es la segunda mitad del

requisito para ser -completo, es necesario demostrar que todos los problemas en , incluso los que no conocemos, se

pueden reducir al problema específico . ¿Cómo podríamos siquiera comenzar a atacar tal labor?. La primera

demostración de que cierto problema efectivamente es -completo es uno de los mayores logros de la teoría de la

computación y de las matemáticas.

El problema de la satisfactibilidad booleana es -completo1. La demostración de este teorema, y de otros que

presentamos aquí sin demostrarlos, se puede hallar en las fuentes que se dan en Notas y referencias al final del capítulo.

Aquí sólo bosquejaremos la idea. La demostración debe mostrar que cualquier problema en se puede reducir a la

satisfactibilidad. La demostración de Steven Cook da un algoritmo para construir una fórmula para una entrada de

tal que la fórmula, en términos informales, describe el cálculo efectuado por un algoritmo no determinista para resolver

al actuar sobre . La fórmula , que es muy larga pero se construye en tiempo acotado por una función polinómica

de la longitud de , se podrá satisfacer si y sólo si el cálculo produce la respuesta sí con algún certificado.

La reducción polinómica es una relación transitiva. Por tanto, si la satisfactibilidad se puede reducir a algún problema

también es -difícil. Si también está en (lo cual por lo regular se puede demostrar fácilmente), entonces es

1 Teorema de Cook - El problema de SAT pertenece a NP dado que puede ser resuelto con una máquina de Turing no determinista que genera todas las

posibles combinaciones de valores para las variables de la expresión y, en forma no determinista intenta verificar si alguna de ellas hace que la expresión se

evalúe en verdadero, en cuyo caso acepta la entrada.

40

-completo. Así, la reducción sirve para demostrar que otros problemas son -completos sin tener que repetir todo el

trabajo del Teorema de Cook. La satisfactibilidad se puede reducir a 3-satisfactibilidad.

La satisfactibilidad (y la 3-satisfactibilidad) son problemas lógicos, y no tienen una relación obvia con los demás

problemas, ni con los muchos otros problemas de optimización que no parecen tener una solución eficiente, algunos en el

campo de los grafos y otros en el de los compiladores y los sistemas operativos. Si los únicos problemas -completos

fueran parecidos al de la satisfactibilidad, la calidad de ser -completo no habríapasado de ser una curiosidad

interesante.

El segundo trabajo crucial en el campo fue el escrito por Richard Karp , quien demostró que los planteamientos como

problemas de decisión de un gran número de problemas de optimización, incluidos varios de los problemas muestra que

describimos antes, también son -completos.

Se requirieron reducciones muy ingeniosas para demostrar que los problemas se podrían reducir a otros al parecer muy

distintos. Karp mostró que la 3-satisfactibilidad se podía reducir (mediante una cadena de reducciones, en algunos casos)

a problemas de grafos que al parecer no tenían ninguna relación, como el del ciclo hamiltoniano y el de coloreado de

grafos.

Esto fue el inicio de una avalancha. Pronto se demostró que muchos problemas para los cuales se estaban buscando

infructuosamente algoritmos polinómicamente acotados eran -completos. De hecho, la lista de problemas -

completos llegó a los centenares en los años setenta.

Como ya dijimos, para demostrar que un problema es -completo basta con demostrar que algún otro

problema -completo se puede reducir polinómicamente a , pues la relación de reducibilidad es transitiva. Por ello, las

diversas partes del teorema se demuestran estableciendo cadenas de transformaciones que parten del problema de la

satisfactibilidad. Presentaremos unas cuantas como modelos.

Muchos se confunden en cuanto a la dirección de la reducción que se requiere para demostrar que un problema es -

completo, por lo que cabe hacer hincapié en que, para demostrar que un problema es -completo, se escoge algún

problema -completo conocido y se reduce a , no al revés. La lógica es la siguiente:

1. Puesto que es -completo, todos los problemas se pueden reducir a P; es decir,

2. Demostrar que .

3. Entonces todos los problemas satisfacen , por la transitividad de las reducciones.

4. Por tanto, es -completo.

El problema de la sumatoria de subconjunto se puede reducir al problema de calendarización de trabajos.

41

ANEXO 6. Problemas y

Algunos de los algoritmos son directos, mientras que otros son complicados y sutiles, pero prácticamente todos

ellos tienen complejidad en donde es el tamaño de las entradas debidamente definido. Desde el punto de

vista adoptado, consideraremos que todos los algoritmos que hemos examinado hasta ahora requieren un tiempo

relativamente corto. Examinemos otra vez la tabla. Ahí vimos que los algoritmos cuya complejidad se describe

con funciones polinómicas simples se pueden ejecutar con entradas relativamente grandes en un tiempo razonable.

La última columna de la tabla muestra que si la complejidad es , el algoritmo de nada sirve a menos que las

entradas sean muy pequeñas. En este apartado nos ocuparemos de problemas cuya complejidad podría describirse

con funciones exponenciales, problemas cuya resolución incluso con los mejores algoritmos conocidos requeriría

muchos años o siglos de tiempo de computadora con entradas moderadamente grandes. Presentaremos

definiciones encaminadas a distinguir entre los problemas dóciles (es decir, “no tan difíciles”) que ya hemos visto

y los renuentes (es decir, “difíciles” o muy tardados). Analizaremos una importante clase de problemas que tienen

una propiedad irritante: ni siquiera sabemos si se pueden resolver de manera eficiente o no.

“ ” es una clase de problemas que se pueden resolver en “tiempo polinómico”. La descripción de “ ” es más

complicada. No se han descubierto algoritmos razonablemente rápidos para estos problemas, pero tampoco se ha

podido demostrar que los problemas requieren mucho tiempo. Dado que muchos de estos problemas son

problemas de optimización que se presentan con frecuencia en aplicaciones, la falta de algoritmos eficientes tiene

importancia real.

6.1 Problemas de decisión

Muchos de los problemas que describiremos en este apartado se dan naturalmente como problemas de

optimización (aunque se les llama problemas de optimización combinatoria), pero también se pueden formular

como problemas de decisión. Las clases , que se definirán, son clases de problemas de decisión.

Básicamente, un problema de decisión es una pregunta que tiene dos posibles respuestas, sí y no. La pregunta se

refiere a alguna entrada. Un ejemplar de problema es la combinación del problema y una entrada específica. Por

lo regular, el planteamiento de un problema de decisión tiene dos partes:

1. La parte de descripción de ejemplar define la información que cabe esperar en la entrada.

2. La parte de pregunta plantea la pregunta tipo “sí o no” en sí; la pregunta contiene variables definidas en

la descripción de ejemplar.

42

La salida de un problema de decisión es sí o bien no según sea la respuesta correcta de la pregunta, aplicada a una

entrada dada. Por ello, podemos ver de manera abstracta un problema de decisión como una correspondencia entre

todas las entradas y el conjunto {sí, no}.

6.1.1 Secuenciación de trabajos con castigos

Supóngase que hay trabajos que deben ejecutarse uno por uno. Se nos dan los tiempos de ejecución

los plazos (medidos a partir de la fecha de inicio del primer trabajo ejecutado) y castigos por

no terminar un trabajo dentro del plazo correspondiente . Supóngase que los tiempos de ejecución,

plazos y castigos son enteros positivos. Un calendario para los trabajos es una permutación de

donde es el trabajo que se efectúa primero, es el que se ejecuta en segundo lugar, y así.

Para un calendario dado, el castigo para el -ésimo trabajo se denota con , y se define como si el

trabajo se termina después de transcurrido el plazo en caso contrario. El castigo total para un

calendario dado es

Problema de optimización: Determinar el castigo más bajo posible (y hallar un calendario óptimo, es decir, uno

que reduzca al mínimo el castigo total).

Problema de decisión: Dado, además de las entradas descritas, un entero no negativo , ¿existe un calendario con

?

La clase . Ninguno de los algoritmos que se conocen para los problemas que acabamos de describir tiene

garantía de ejecutarse en un tiempo razonable. No definiremos “razonable” de forma rigurosa, pero sí definiremos

una clase de problemas que incluye a los que tienen algoritmos razonables.

Decimos que un algoritmo está polinómicamente acotado si su complejidad de peor caso está acotada por una

función polinómica del tamaño de las entradas (es decir, si existe un polinomio tal que, para toda entrada de

tamaño , el algoritmo termine después de cuando más pasos), y si existe un algoritmo polinómicamente

acotado para resolverlo.

43

sólo está definida para problemas de decisión. Podría parecer un tanto extravagante utilizar la existencia de una

cota de tiempo polinómica como criterio para definir la clase de problemas más o menos razonables: los

polinomios pueden ser muy grandes. No obstante, hay varias razones de peso para hacerlo.

En primer lugar, si bien no es verdad que todos los problemas en tengan un algoritmo de eficiencia aceptable, sí

podemos asegurar que, si un problema no está en , será extremadamente costoso y probablemente imposible de

resolver en la práctica. Es probable que ninguno de los problemas que describimos esté en ; no existen

algoritmos para resolverlos que se sepa estén polinómicamente acotados, y la mayoría de los investigadores en el

campo piensan que no existen tales algoritmos. Es factible que la definición del hecho de estar o no en sí es un

criterio útil en el caso de problemas renuentes.

Un segundo motivo para usar una cota polinómica para definir es que los polinomios tienen bonitas propiedades

de “cierre”. Podríamos obtener un algoritmo para un problema complejo combinando varios algoritmos para

problemas más sencillos. Algunos de los algoritmos más simples podrían trabajar con las salidas o los resultados

intermedios de otros. La complejidad del algoritmo compuesto podría estar acotada por la suma, multiplicación y

composición de las complejidades de sus algoritmos componentes. Puesto que los polinomios están cerrados bajo

estas operaciones, cualquier algoritmo que se construya de diversas formas naturales a partir de varios algoritmos

polinómicamente acotados también estará polinómicamente acotado. Ninguna clase más pequeña de funciones

que sean cotas de complejidad útiles tiene estas propiedades de cierre.

Un tercer motivo para emplear una cota polinómica es que hace a independiente del modelo de cómputo formal

específico que se use. Se usan varios modelos formales (definiciones formales de algoritmos) para demostrar

teoremas rigurosos acerca de la complejidad de los algoritmos y problemas. Los modelos difieren en cuanto al

tipo de operaciones permitidas, los recursos de memoria disponibles y los costos asignados a diferentes

operaciones. Un problema que requiere ) pasos con un modelo podría requerir más de pasos con

otro, pero en el caso de prácticamente todos los modelos realistas, si un problema está acotado polinómicamente

con uno, estará acotado polinómicamente con los demás.

La clase . Muchos problemas de decisión (incluidos todos los que hemos puesto de muestra) se plantean como

preguntas de existencia: ¿Existe una asignación de verdad que haga verdadera una fórmula dada? Para una

entrada dada, una “solución” es un objeto (por ejemplo una asignación de verdad) que satisface los criterios del

problema y por tanto justifica una respuesta de sí (por ejemplo, la asignación de verdad hace que la fórmula

sea verdadera). Una “solución propuesta” no es más que un objeto del tipo apropiado: podría satisfacer o no los

criterios.

44

A veces se usa el término certificado para referirse a una solución propuesta. En términos informales, es la

clase de problemas de decisión para los que una solución propuesta dada con una entrada dada se puede verificar

rápidamente (en tiempo polinómico) para determinar si realmente es una solución (es decir, si satisface los

requisitos del problema). Más formalmente, las entradas de un problema y las soluciones propuestas se deberán

describir con cadenas de símbolos de algún conjunto finito, por ejemplo, el conjunto de caracteres del teclado de

una terminal de computadora. Necesitamos algunas convenciones para describir grafos, conjuntos, funciones, etc.,

que usan tales símbolos. El conjunto de convenciones que se adopta para un problema dado es la codificación de

ese problema. El tamaño de una cadena es el número de caracteres que contiene.

Algunas cadenas de símbolos del conjunto escogido no son codificaciones válidas de objetos pertinentes al

problema en cuestión; sólo son basura. En términos formales, una entrada de un problema y una solución

propuesta para ese ejemplar del problema pueden ser cualquier cadena formada a partir del conjunto de caracteres.

La verificación de una solución propuesta incluye verificar que la cadena tenga sentido (es decir, que tenga la

sintaxis correcta) como descripción del tipo de objeto requerido, además de verificar que satisfaga los criterios del

problema. Por tanto, cualquier cadena de caracteres puede verse como un certificado para un ejemplar de un

problema.

Podría haber problemas de decisión para los que no haya una interpretación natural de las “soluciones” o las

“soluciones propuestas”. En lo abstracto, un problema de decisión no es más que una función que relaciona un

conjunto de cadenas de entrada con el conjunto í . Una definición formal de considera todos los

problemas de decisión. La definición emplea algoritmos no deterministas, que definiremos a continuación.

Aunque tales algoritmos no son realistas ni útiles en la práctica, sirven para clasificar los problemas.

Algoritmo no determinista. Un algoritmo no determinista tiene dos fases y un paso de salida:

1. La fase de “conjetura” no determinista. Se escribe alguna cadena totalmente arbitraria de caracteres, ,

principiando en algún lugar designado de la memoria. Cada vez que se ejecuta el algoritmo, la cadena que

se escribe podría ser distinta. (Esta cadena es el certificado; podría considerarse como una conjetura de la

solución del problema, por lo que podríamos llamar a ésta la fase de conjetura, pero s bien podría ser sólo

basura.)

2. La fase de “verificación” determinista. Comienza a ejecutarse una subrutina determinista (o sea,

ordinaria). Además de las entradas del problema de decisión, la subrutina podría usar , o podría hacer

caso omiso de s. Tarde o temprano devolverá un valor de verdadero o falso, o podría entrar en un ciclo

infinito y nunca parar. (Podemos pensar en la fase de verificación como un examen de s encaminado a

determinar si es una solución para las entradas del problema de decisión, es decir, si justifica una

respuesta de sí para las entradas del problema de decisión.)

45

3. El paso de salida. Si la fase de verificación devolvió verdadero, el algoritmo produce sí. De lo contrario,

no se produce ninguna salida.

El número de pasos que se ejecutan durante una ejecución de un algoritmo no determinista se define como la

suma de los pasos de las dos fases; es decir, el número de pasos que se ejecutan para escribir (que es

simplemente el número de caracteres de ) más el número de pasos que ejecuta la segunda fase determinista.

También podemos describir un algoritmo no determinista con una estructura de subrutina explícita.

Supóngase que genCertif genera un certificado arbitrario.

void aNoDet(String entrada)

String s genCertif();

boolean revisOK verifA(entrada, s);

if (revisOK)

Enviar a la salida “sí”.

return;

Normalmente, los algoritmos terminan con todas las entradas y cada vez que ejecutamos un algoritmo con la

misma entrada obtenemos la misma salida. Esto no sucede con los algoritmos no deterministas; con una entrada

específica , la salida (o ausencia de salida) de una ejecución podría diferir de la de otra porque podría depender

de . Entonces, ¿qué “respuesta” calcula un algoritmo no determinista, digamos , para un problema de decisión

dado con la entrada ?. La respuesta de con se define como sí si y sólo si existe alguna ejecución de A que

produzca sí como salida. La respuesta es no si, para toda , no se produce salida. Utilizando nuestro concepto

informal de s como una solución propuesta, la respuesta de con es sí si y sólo si existe alguna solución

propuesta que “funcione”.

es la clase de problemas de decisión para la cual existe un algoritmo no determinista polinómicamente

acotado. (El nombre proviene de “No determinista Polinómicamente acotado”.)

Demostración Un algoritmo ordinario (determinista) para resolver un problema de decisión es, con una

modificación menor, un caso especial de un algoritmo no determinista. Si es un algoritmo determinista para

resolver un problema de decisión, basta con hacer que sea la segunda fase de un algoritmo no determinista, pero

modificándolo de modo que, en todos los casos en que produciría la salida sí, devuelva verdadero, y en todos los

casos en que produciría la salida no, devuelva falso. simplemente hará caso omiso de lo que haya escrito la

primera fase y procederá a efectuar su cálculo acostumbrado. Un algoritmo no determinista puede ejecutar cero

46

pasos en la primera fase (escribiendo la cadena nula) de modo que, si se ejecuta en tiempo polinómico, el

algoritmo no determinista que tiene el A modificado como segunda fase también se ejecutará en

tiempo polinómico. Producirá si lo habría hecho, y no producirá nada en caso contrario.

La pregunta importante es, ¿ o es un subconjunto propio de ? Dicho de otro modo, ¿es el no

determinismo más potente que el determinismo en el sentido de que algunos problemas se pueden resolver en

tiempo polinómico con un “conjeturador” no determinista pero no se pueden resolver en tiempo polinómico con

un algoritmo ordinario? Si un problema está en , con una cota de tiempo polinómico, digamos p, podremos dar

(de forma determinista) la respuesta correcta (sí o no) si verificamos todas las cadenas cuya longitud no sea mayor

que (es decir, ejecutamos la segunda fase del algoritmo no determinista con cada una de las cadenas

posibles, una por una). El número de pasos requeridos para verificar cada cadena es cuando más . El

problema es que hay demasiadas cadenas que verificar. Si nuestro conjunto de caracteres contiene c caracteres,

habrá denas de longitud . El número de cadenas es exponencial, no polinómico, en Claro que hay

otra forma de resolver problemas: usar algunas de las propiedades de los objetos en cuestión y un poco de ingenio

para idear un algoritmo que no tenga que examinar todas las posibles soluciones. Al ordenar, no verificamos cada

una de las permutaciones de las claves dadas para ver cuál coloca las claves en orden. La dificultad, en el

caso de los problemas que tratamos, estriba en que tal enfoque no ha producido algoritmos eficientes; todos los

algoritmos conocidos examinan todas las posibilidades o bien, si se valen de ardides para reducir el trabajo, tales

ardides no son lo bastante buenos como para dar pie a algoritmos polinómicamente acotados.

Se cree que es un conjunto mucho más grande que , pero no existe un solo problema en para el cual se

haya demostrado que el problema no está en . No se conocen algoritmos polinómicamente acotados para muchos

problemas que están en , pero no se han demostrado cotas inferiores mayores que las polinómicas para esos

problemas. Por tanto, la pregunta que hicimos antes, ¿es ? sigue pendiente.

El tamaño de las entradas. Consideremos el problema siguiente problema: Dado un entero positivo , ¿existen

enteros tales que ? (es decir, ¿es no primo?). ¿Este problema está en ? Consideremos el

algoritmo siguiente, que busca un factor de .

factor = 0

for (j 2; j n; j)

if ((n mod j) 0)

factor = j;

break;

47

return factor;

El cuerpo del ciclo se ejecuta menos de veces, y es indudable que se puede evaluar en , así

que el tiempo de ejecución del algoritmo está holgadamente en . Sin embargo, no se sabe que el problema

de determinar si un entero es primo o es factorizable esté en y, de hecho, la dificultad para hallar factores de

enteros grandes es la base de varios algoritmos de cifrado precisamente porque se le considera un problema

difícil. ¿Cómo resolvemos esta aparente paradoja?

La entrada del algoritmo para probar primos es el entero pero, ¿qué tamaño tiene la entrada?

Hasta ahora, hemos utilizado cualquier medida cómoda y razonable del tamaño de las entradas; no era importante

contar caracteres o bits individuales. Si nuestra medida del tamaño de una entrada podría marcar la diferencia

entre si un algoritmo es polinómico o es exponencial, hay que tener más cuidado. El tamaño de una entrada es el

número de caracteres que se requieren para escribirla. Si , escribimos tres dígitos, no 150 dígitos. Así

pues, un entero n escrito en notación decimal tiene un tamaño aproximado de . Si optamos por considerar

la representación interna en una computadora, donde los enteros se representan en binario, el tamaño de n será

aproximadamente . Estas representaciones difieren en un factor constante;

es decir, , así que no es crucial cuál representación usemos. Lo que sí es importante es

que, si el tamaño s de las entradas es y el tiempo de ejecución de un algoritmo es n, el tiempo de ejecución

del algoritmo será una función exponencial del tamaño de las entradas . Por tanto, el algoritmo anterior

para determinar si n es primo no está en . No se conocen aún algoritmos para probar primos en tiempo

polinómico. Sin embargo, la pregunta: “¿El entero n es primo?” está en .

En los problemas que examino, la variable que usábamos para describir el tamaño de las entradas correspondía

(aproximadamente) a la cantidad de datos contenida en ellas. Usamos como tamaño de la entrada al ordenar una

lista de claves. Cada una de las claves se representaría, digamos, en binario, pero dado que hay claves, habrá

por lo menos n símbolos en la entrada. Por tanto, si la complejidad de un algoritmo está acotada por un polinomio

en n, estará acotada por un polinomio en el tamaño exacto de la entrada.

Asimismo, usamos como el tamaño de las entradas de grafos, pero es necesario enumerar explícitamente

todas las aristas, lo cual requiere al menos símbolos en la entrada. Aunque no es necesario enumerar los n

vértices en la entrada, en todos los problemas de interés todo vértice incide en alguna arista, así que es

cuando más tres veces el número de símbolos que hay en la entrada. Una vez más, si la complejidad de un

algoritmo está acotada por un polinomio en estará acotada por un polinomio en el tamaño exacto de la

entrada.

48

Si dos medidas del tamaño de las entradas están acotadas cada una por una función polinómica de la otra,

determinar si el problema está en no dependerá de la medida específica que se use.

En ordenamiento, si una medida es el número de claves , y la otra es (clave máxima), que cuenta bits

individuales, tendremos y ). Por tanto, cada una de las

medidas no está a más de una función polinómica de la otra.

Por ello, normalmente no tenemos que especificar con toda precisión el tamaño de las entradas.

No obstante, debemos tener cuidado en los casos en que el tiempo de ejecución de un algoritmo se expresa como

función polinómica de uno de los valores de entrada, como sucede con el problema de la prueba de primos.

Unos cuantos de los problemas de muestra que describimos antes tienen soluciones de programación dinámica

que a primera vista parecen estar polinómicamente acotados pero, al igual que el programa de prueba de primos,

no lo están. Recordemos el problema de la sumatoria de subconjunto: ¿Existe un subconjunto de los objetos con

tamaños cuya suma sea exactamente ? Si utilizamos las técnicas, podremos resolver este problema

con una tabla de por y sólo requeriremos unas cuantas operaciones para calcular cada elemento de la tabla.

Existen soluciones de programación dinámica similares para diversas versiones del problema de la mochila.

La solución de programación dinámica para el problema de la suma de subconjunto se ejecuta en tiempo

Puesto que hay objetos en la entrada, el término no representa ningún problema, pero el valor del número es

exponencialmente mayor (en general) que la entrada, porque el dato en la entrada se representaría con bits.

Por ello, la solución de programación dinámica no es un algoritmo polinómicamente acotado. Desde luego, si

no es demasiado grande, el algoritmo podría ser útil en la práctica.

49

ANEXO 7. Proposiciones y variables lógicas

La lógica es la herramienta que usan las matemáticas para desarrollarse. El objetivo del mismo es describir en qué

consiste una teoría matemática. Para lograrlo, primero hay que exponer sucintamente las reglas de la lógica de

proposiciones, definir con precisión que es un razonamiento lógico y, por último, explicar en qué consiste su

aplicación en el desarrollo del trabajo de investigación (brevemente, una serie de axiomas, definiciones y

teoremas relacionados entre sí mediante argumentos lógicos usados para sustentar la hipótesis propuesta).

La lógica es un esquema de reglas que permite deducir verdades a partir de otras verdades. El medio que lleva de

las primeras verdades a las otras deducidas se llama razonamiento lógico. La lógica analiza, los razonamientos

lógicos, estableciendo cuando un razonamiento es válido, independientemente del contenido de las verdades que

se enuncien. Solo le interesan las manipulaciones que se hacen con los enunciados, no su contenido.

Todos los resultados mostrados en se prueban rigurosamente. Sin embargo, no se usa para ello el razonamiento

lógico, sino el simple y eficaz camino de las tablas introducidas. Por supuesto, algunos resultados sí se podrían

demostrar a partir de otros anteriores mediante las leyes del algebra de proposiciones, que se exponen. Se prefiere

dejar todo en manos de las tablas, pues en el resto de la investigación son los argumentos lógicos los

protagonistas. Por contra, aunque no se habla de axiomas, definiciones y teoremas en las teorías matemáticas,

desde el principio llamados teoremas a los resultados que se obtuvieren y se podrán visualizar en el anexo

Teoremas.

Proposiciones y variables lógicas. Puesto que la lógica busca deducir verdades a partir de otras verdades, su

materia prima son los enunciados de esas verdades. Eso es lo que se llama proposiciones: un enunciado que se

puede juzgar como verdadero o falso.

Los siguientes enunciados “la máquina está disponible”, “el inventario es suficiente” y “el operario está libre”

son proposiciones, pues se puede juzgar objetivamente que son falsas o verdaderas. Deliberadamente no se escribe

una definición formal del concepto de proposición en nuestra teoría por dos razones. Primero, en muchos casos es

cuestión de opinión si un enunciado se puede juzgar como verdadero o falso, o simplemente, el juicio no será

unánime. La segunda razón es que las proposiciones no son parte de la lógica. Son los ladrillos con los que se

construyen los razonamientos lógicos. La lógica se ocupa de las relaciones entre las proposiciones, no de su

contenido.

Es de interés particular, pues, asignar a cada proposición un valor binario, previa validación de la variable de

estado. Por ello se debe usar símbolos que representen proposiciones cualesquiera y examinar las relaciones entre

estos símbolos independientemente de corroborar su registro particular.

50

Se utilizara letras latinas minúsculas, especialmente . ., para representar proposiciones cualesquiera. La

única característica que nos recuerda que representan proposiciones es que estos símbolos pueden tener dos

valores: verdadero (representado por ) o falso (representado por ). Y como representan proposiciones

cualesquiera, pueden tomar cualquiera de los dos. Estos símbolos no son proposiciones sino variables discretas,

que comúnmente construyen recursivamente las formulas atómicas usadas en la lógica proposicional. Entre estas

variables lógicas discretas para una planta de producción, se definen las materias primas y proceso ( ), equipos

( ), la mano de obra ( ), pertenecientes a cada a centros de trabajo ( ) y productos ( ).

Sin embargo, una vez aclarada la diferencia entre proposiciones y variables lógicas, y puesto que una variable

lógica representa una proposición cualquiera, se empleara los dos términos indistintamente. El análisis utilizando

la lógica va a consistir en analizar variables lógicas y describir las relaciones entre ellas. La relación más sencilla

es la de variables dependientes e independientes. Dos variables lógicas son dependientes si el valor que tome una

condiciona el valor que puede tomar la otra. Son independientes si no son dependientes.

Al representar las variables lógicas por letras como . . Si en una expresión aparecen las variables y

ambas pueden tomar los valores y , y se tiene un total de cuatro combinaciones posibles de los valores de y

. Al tener tres variables, hay ocho posibilidades Una tabla de verdad, o simplemente tabla en este contexto,

es una representación en filas y columnas de los valores de algunas variables lógicas. Cada columna representa

una variable, y cada fila una posible combinación de los valores de las mismas. En la tabla 5 se muestran todas las

posibles combinaciones de los valores y para tres variables.

Una variable lógica puede, en principio, tomar los valores 0 o . Sin embargo, es posible que una variable

dependiente de otras, cuyo valor queda condicionado por estas, tome siempre el valor 1 (verdadero) para cualquier

situación de las variables de las que depende. O bien, otra variable que tome siempre el valor 0 (falso). Las

variables con este comportamiento reciben un nombre. Se llama tautología a la variable lógica, dependiente de

otras, la cual toma el valor 1 independientemente del valor de las variables de las que depende. Análogamente se

llama contradicción a la variable lógica cuyo valor es 0 en cualquier situación.

Tabla 1. Combinaciones de los valores y

p q r

0 0 0

0 0 1

0 1 0

0 1 1

1 0 0

1 0 1

51

1 1 0

1 1 1

1.1.1. Conectivos lógicos

Los conectores permiten construir nuevas proposiciones a partir de unas dadas. La nueva proposición es

dependiente de las proposiciones con las que se construye. Un conector monario llamado negación el cual, a partir

de una proposición, construye otra. También varios conectores binarios, que a partir de dos proposiciones dan

otra: conjunción, disyunción, implicación y doble implicación. En los cinco casos se dará una explicación intuitiva

seguida de una descripción formal.

La descripción formal consiste en describir exactamente como depende la nueva proposición de las proposiciones

con que se construye. La descripción se hace mediante tablas en las que aparecen todas las combinaciones

posibles de valores que toman las variables independientes. Inicialmente la negación de una proposición, que es

otra proposición con valor opuesto a la primera. Si la primera es cierta, su negación es falsa y viceversa.

En términos de variables lógicas, la negación de una variable es otra variable dependiente de la primera porque su

valor está determinado por el de ella.

La negación de una proposición , denotada , es la proposición cuyo valor es el opuesto al de . Se puede

definir la negación mediante la tabla 6. En ella se indica, para cada valor de la proposición , el valor que toma la

proposición

Tabla 2. Negación de una proposición

0 1

1 0

La conjunción es un conector binario que funciona como la conjunción copulativa “ ” del español. La conjunción

de dos proposiciones, entonces, es una proposición que es cierta si ambas son ciertas, y es falsa si alguna de ellas

es falsa. La conjunción de dos proposiciones denotada es la proposición que solo es cierta si ambas

son ciertas. En un proceso de producción donde las máquinas están dispuestas en serie se podrá expresar en

términos de la conjunción. La descripción mediante la tabla 7 consiste ahora en ilustrar, para cada valor que

pueden tomar las proposiciones y el valor que resulta en la proposición

Tabla 3. Conjunción de dos proposiciones denotada

52

0 0 0

0 1 0

1 0 0

1 1 1

La disyunción es el conector que opera de forma parecida a la conjunción disyuntiva “ ” del español. La

disyunción de dos proposiciones es otra proposición que es cierta si alguna de las dos originales es cierta. Es

decir, basta que una de ellas sea cierta para que la disyunción lo sea. Sin embargo en lógica se emplea en sentido

inclusivo como se aprecia en la tabla que la define. En un proceso de producción donde las máquinas están

dispuestas en paralelo se podrá expresar en términos de la disyunción. La disyunción de dos proposiciones ,

denotada , es la proposición que solo es falsa si ambas son falsas. En forma de tabla 8.

Tabla 4. disyunción de dos proposiciones , denotada

0 0 0

0 1 1

1 0 1

1 1 1

El siguiente conector que se introduce es la implicación, que tiene gran importancia en la lógica pues es la base

del razonamiento deductivo. Requiere un poco de atención para entender bien su descripción formal que, al

principio, no parece responder a la intuición. Cuando se afirma que una proposición implica otra se quiere

expresar el hecho de que si la primera es cierta, entonces la segunda debe ser cierta también.

En el lenguaje corriente se usa la expresión “Si . . . entonces . . . ”. Las dos proposiciones que aparecen en la

implicación se llaman antecedentes y consecuentes. El antecedente es la condición que, si es cierta, asegura que se

cumple el consecuente. Base del lenguaje PWL, la setencia if... Then.. en cualquier lenguaje de

programación.

Decir qué valor tiene la implicación en cada caso de los posibles valores de antecedente y consecuente. Es claro

que quiero decir que una implicación es cierta si el antecedente es cierto y el consecuente también. Por todo ello

se define la implicación del siguiente modo. La implicación de dos proposiciones denotada es la

proposición que solo es falsa si es verdadera y es falsa. La tabla 9 correspondiente es:

Tabla 5. La implicación de dos proposiciones denotada

53

0 0 1

0 1 1

1 0 0

1 1 1

Es fácil convencerse de que la proposición no es la misma que . Esta observación es suficientemente

importante como para asignar nombres a cada una de estas implicaciones.

Dada una implicación , se otorgan nombres a las siguientes implicaciones:

implicación directa,

implicación inversa,

implicación reciproca,

implicación contrapositiva.

El último conector que se introduce es el de doble implicación o bicondiciónal. Como su nombre indica, si dos

proposiciones están relacionadas con el conector doble implicación, significa que una implica la otra y la otra la

una. Entonces, si una de ellas es cierta, la otra debe serlo también, que es lo mismo que decir que si una es falsa la

otra también. La doble implicación de dos proposiciones denotada es la proposición que solo es

verdadera si ambas coinciden en su valor. De la tabla 10 resulta :

Tabla 6. La doble implicación de dos proposiciones denotada

0 0 1

0 1 0

1 0 0

1 1 1

Una explicación que se enuncia a partir de la doble implicación es la de variables lógicas equivalentes. Dos

variables son equivalentes si son dependientes de modo que siempre toman el mismo valor. Si una es verdadera,

entonces la otra también y viceversa. Es claro que el conector de doble implicación puede ayudar a expresar esta

idea. Una forma de hacerlo es decir que la doble implicación entre dos proposiciones equivalentes es siempre

cierta. Dos variables y son equivalentes, y se denota , si es una tautologıa. (Barnes, 1978)

Es claro que en cualquier expresión puedo sustituir una proposición por otra equivalente, y la nueva expresión que

obtengo es equivalente a la original pues los valores son los mismos. De ahí que el concepto de proposiciones

equivalentes sea importante y muy utilizado en lógica. Ahora se puede enunciar un primer resultado sencillo pero

54

muy útil en la teoría y en la práctica de la lógica. Es la relación entre las implicaciones directa, inversa, reciproca

y contrapositiva. Ver anexo Teorema 19.

Otro teorema relacionado con el concepto de equivalencia es la que dice que el conector doble implicación es

equivalente a la implicación directa junto con la implicación inversa. Es la formulación precisa de lo que el

símbolo ↔ expresa abiertamente. Ver anexo Teorema 20.

En las expresiones que incluyen algunos o todos los operadores , en la ausencia de paréntesis, primero se

evalúa después y luego . Esta convención se conoce como precedencia del operador. En álgebra, la

precedencia del operador indica que se evalúan y antes que y –.

1.1.2. Leyes del algebra proposicional

Los conectores entre proposiciones (negación, conjunción, disyunción, etc.) se pueden ver, desde un punto de

vista algebraico, como operaciones definidas en el conjunto de las proposiciones. Se toma una proposición (en el

caso de la negación) o dos proposiciones (en los otros casos) y se operan, obteniendo como resultado otra

proposición. Resulta imperativo analizar algunas propiedades algebraicas de estas operaciones como son la

aplicación reiterada, asociatividad, conmutatividad, existencia de elemento neutro, etc. (Badesa C, 1998)

Como primer paso se observa que los conectores de implicación y doble implicación se pueden escribir en

términos de la negación, conjunción y disyunción solamente. Entonces bastara con analizar las propiedades

algebraicas de estas tres operaciones. (En realidad, también el conector de disyunción se puede expresar en

función del de conjunción y el de negación, pero estos tres en conjunto tienen más y mejores propiedades

algebraicas. Ver anexo Teorema 21.

Puesto que en el teorema que la doble implicación es equivalente a la implicación directa y la inversa, entonces la

doble implicación también se puede expresar solo con negación, conjunción y disyunción. En definitiva, se darán

uso a las propiedades de la negación, la conjunción y la disyunción.

Propiedades de la negación. Debido a que la negación es una operación monaría, la única propiedad que en este

caso puede analizarse es la aplicación reiterada. El resultado es muy evidente por estar trabajando con

proposiciones que solo pueden tomar dos valores. La negación es cambiar el valor de una proposición, y como

solo hay dos posibilidades, si se cambia dos veces se regresa al valor original. Ver anexo Teorema 22.

55

Propiedades de la conjunción. La conjunción es una operación binaria y en ella sí procede analizar más

propiedades. La idempotencia, da el resultado de operar una proposición consigo misma. La asociatividad nos

indica cómo se puede efectuar la conjunción de tres proposiciones. La conmutatividad muestra que el orden de las

proposiciones en una conjunción es irrelevante. Existe un elemento neutro (la proposición con valor 1, que se

denota simplemente como 1) que al operarlo con cualquier proposición da como resultado la misma proposición.

Existe también un elemento dominante (la proposición con valor 0, que se denota simplemente como 0) que

operado con cualquier proposición arroja el resultado 0. Ver anexo Teorema 23.

La presencia de la propiedad asociativa permite definir el símbolo , sin paréntesis, como o bien

puesto que son iguales. El resultado en ambos casos es que solo es cierto si las tres

proposiciones y son ciertas. Generalizando esta idea se define la conjunción de las variables

denotada como la variable que solo es cierta si todas las variables

son ciertas. Las

propiedades asociativa y conmutativa aseguran que la descripción es coherente con la anterior.

Propiedades de la disyunción. El análisis de la disyunción sigue los mismos pasos que el de la conjunción pues

las propiedades que satisfacen son las mismas. La única diferencia es que los papeles de y , como elementos

neutro y dominante respectivamente, se invierten ahora. Ver anexo Teorema 24.

Las propiedades asociativa y conmutativa aseguran que la explicación es coherente con la descripción de la

disyunción de dos variables.

Propiedades de las operaciones combinadas. Ahora se estudian algunas propiedades que surgen al considerar

expresiones con dos o las tres operaciones combinadas. Ver anexo Teorema 25.

La simplificación de una proposición mediante manipulaciones algebraicas. Cada proposición es equivalente a la

anterior por la ley algebraica que se indica a su lado.

proposición a simplificar

segunda ley de De Morgan

doble negación y conmutatividad

distributividad

complementariedad de la negación

1 neutro de .

Prueba algebraica de la ley de absorción (suponiendo probadas las leyes algebraicas anteriores). Partiendo de la

proposición mediante pasos algebraicos se llega a que es equivalente a la proposición .

56

0 neutro de _

comp. de negación

distributividad

distributividad

idemp. y complemento

distrib., idemp. y dominación

complemento y 1 neutro de ^

0 neutro de .

Cuantificadores. Se introducen los enunciados abiertos y, tras ellos, los cuantificadores. Son elementos muy

habituales en la formulación de definiciones y resultados en matemáticas en expresiones de la forma “para todo

numero entero. . . ” o “existe una función tal que . . . ”.

Se llama abierto a un enunciado que contiene variables que toman valores en un conjunto dado, llamado universo,

de forma que para cada valor que tomen las variables, el enunciado se convierte en una proposición.

Un enunciado abierto no es una proposición por sí mismo, sino que se convierte en una cuando las variables

toman un valor. En el caso anterior, el enunciado puede ser verdadero o falso según los valores que tome la

variable.

Puesto que las proposiciones se representan por letras , los enunciados abiertos se representan por

símbolos como donde son las variables que contiene el enunciado.

Los cuantificadores son unos prefijos que, antepuestos a enunciados abiertos los convierten en proposiciones. Se

utilizan dos: el cuantificador universal y el cuantificador existencial. El primero se simboliza por , y se suele

leer “para todo”. Indica que el enunciado que le sigue debe ser cierto para todos los posibles valores de la

variable. El segundo se simboliza por , y se lee “existe algún”.

Indica que el enunciado que sigue es cierto para, al menos, uno de los valores que puede tomar la variable.

Tomar su propiedad de convertir enunciados abiertos en proposiciones como base para dar una aclaración.

Si es un enunciado abierto que depende de la variable , la cual toma valores en un conjunto universo dado,

definir el símbolo como la proposición que es cierta solo si el enunciado abierto es verdadero para todos

los valores que la variable puede tomar en su universo.

a. Se define el símbolo como la proposición que es cierta si el enunciado abierto es verdadero para

algún valor de los que la variable toma en su universo.

b. La proposición no es en realidad otra cosa que una conjunción, mientras que se trata de

una disyunción como se aprecia a continuación.

57

La necesidad de introducir los cuantificadores aparece cuando los posibles valores de la variable no se pueden

enlistar como en el caso anterior: si ahora toma valores en los numeros reales, no se puede escribir de

otro modo. Para usar cuantificadores basta recordar que un cuantificador junto a un enunciado abierto es una

proposición y, a partir de ahí, se maneja como cualquier otra proposición. Sin embargo hay algunas reglas que

simplifican el uso de proposiciones que contienen cuantificadores. En concreto se analizara dos de ellas: la

negación de proposiciones con cuantificadores y la combinación de cuantificadores. (Enderton, 1972)

Una proposición que comienza con el cuantificador universal necesita que el enunciado abierto sea cierto para

todos los valores de la variable, por tanto basta con que en un valor sea falso para que toda la proposición sea

falsa. Por ello, la negación con un cuantificador universal nos lleva a un cuantificador existencial y viceversa. Al

recordar que es una conjunción y es una disyunción, esto no es otra cosa que las leyes de De

Morgan vistas en el teorema. El resultado preciso se recoge en el siguiente teorema. Ver anexo Teorema 26.

Las primera y segunda reglas nos dicen que combinar cuantificadores universales y combinar cuantificadores

existenciales es conmutativo. Ver anexo Teorema 27.

Gracias a este resultado se puede escribir sin ambigüedad , y o en lugar de , ası como y o

en lugar de , y el orden de las variables e es irrelevante. Sin embargo hay que tener cuidado pues el

orden si es importante cuando se combinan cuantificadores de ambos tipos. (Ershov, 1990)

Para terminar se define el cuantificador de existencia y unicidad, simbolizado . Como su nombre indica este

símbolo contiene dos afirmaciones: primero, la existencia de un elemento que cumple el enunciado; segundo, que

dicho elemento es el único que lo cumple. La forma de enunciar la unicidad es diciendo que si hay dos elementos

que cumplen la propiedad, entonces son iguales. Si es un enunciado abierto, el símbolo es la

proposición definida por

1.1.3. El razonamiento lógico

Finalmente el objetivo de la lógica: obtener proposiciones verdaderas a partir de otras proposiciones verdaderas ya

conocidas. Esta deducción se efectúa mediante lo que se llama un razonamiento lógico. Por ello, se define que es

un razonamiento lógico y cómo construirlo. La finalidad no es desarrollar la capacidad de crear nuevos

razonamiento lógicos, sino poder analizar razonamientos ya hechos y determinar si son correctos.

Lo que se pretende con un razonamiento lógico es deducir una proposición verdadera nueva a partir de otras

proposiciones verdaderas ya conocidas. Al analizar esta idea, empezando por nombrar sus elementos. Las

58

proposiciones que son conocidas se llaman hipótesis o premisas. La proposición que se deduce es la tesis,

resultado o consecuencia. El hecho de que las premisas nos lleven a deducir la consecuencia se puede expresar por

medio de una implicación: si las premisas son ciertas, entonces la consecuencia debe ser cierta.

Si son las premisas y es la consecuencia, quiero expresar la idea de que si todas las premisas son

ciertas, entonces la consecuencia es cierta. Es decir .

Nos interesa el razonamiento lógico independientemente del contenido de las proposiciones. Si es cierto que de

las premisas se sigue necesariamente la consecuencia , entonces la expresion

debe ser siempre verdadera.

Una proposición de la forma es un razonamiento lógico si es una tautología. Entonces el

razonamiento se denota las proposiciones se llaman premisas y la

proposición consecuencia.

Al considerar las proposiciones: “si un numero entero no es cero, entonces su valor absoluto es positivo” y “

no es cero”. Puedo deducir que el valor absoluto de −4 es un número positivo. Pero la deducción no depende de

que estar hablando acerca del valor absoluto de números enteros, sino de su estructura lógica. Las premisas son

(“si un numero entero no es cero, entonces su valor absoluto es positivo”) y (“un numero entero, , no

es cero”), es decir, y la consecuencia es (“su valor absoluto, es positivo”). El razonamiento

ha sido y es valido sean quienes sean y

Por ello tiene nombre propio: modus ponendo ponens (del latın, que se puede traducir como el razonamiento que

afirmando (ponendo) afirma (ponens)).

Con la misma implicación de antes “si un numero entero no es cero, entonces su valor absoluto es positivo” y

además con la proposición “el valor absoluto del numero a no es positivo”, puedo deducir que “el numero a es

cero”. El razonamiento en este caso ha sido y se llama modus tollendo tollens (el

razonamiento que negando (tollendo) niega (tollens).

Este razonamiento, cuya estructura es se llama silogismo.

La pregunta ahora es, dado una expresión de la forma ¿como saber si es un razonamiento

lógico o no? Las dos formas de probar que es un razonamiento lógico son: Primera, demostrar directamente que

dicha proposición es una tautología, mediante una tabla, parte de la investigación es expresar que el problemas

es una tautologia. Es útil para razonamientos sencillos, cuyas tablas no sean grandes. Segunda,

descomponer el razonamiento en razonamientos más simples ya conocidos. Es decir, partiendo de las premisas y

59

aplicando razonamientos simples conocidos ir deduciendo nuevas proposiciones ciertas hasta llegar a la que se

enunciaba como consecuencia. Este segundo es el método habitual de probar la validez de razonamientos lógicos

complejos. (Van Dalen, 1983)

Para poder utilizar cadenas de razonamientos simples en la prueba de un razonamiento complicado se necesita

tener algunos razonamientos ya demostrados de forma directa. Se exponen algunos de estos razonamientos que

son muy habituales y, prácticamente, se podría decir que responden en gran medida al sentido común: se llaman

reglas de inferencia y tienen nombres propios. Ver anexo Teorema 28. (Enderton, 1972)

Aunque tal vez haya un camino más corto para determinar los valores de verdad de una proposición formada al

combinar las proposiciones usando operadores como y , la tabla de verdad siempre proporcionará

todos los valores de verdad posibles de para diferentes valores de las proposiciones que la constituyen .

60

ANEXO 8. El poder de los lenguajes de programación

Como aplicación práctica de la teoría presentada, regresamos a nuestra pregunta con respecto al poder expresivo

de los lenguajes de programación. Lo que nos concierne ahora seria la cuestión de que aspectos deben incluirse en

un lenguaje de programación, para garantizar que una vez diseñado e implementado no descubramos que existen

problemas computables cuyas soluciones no pueden especificarse con dicho lenguaje. Al concebir el lenguaje a

utilizar sea en código binario, y las instrucciones se ejecuten como un sistema lógico computable, con lo cual se

optimizaría en parte la problemática de expresar un algoritmo que sea recursivo o decidible.

La estrategia consistirá en desarrollar un lenguaje de programación esencial, con el cual se pueda expresar un

programa para calcular cualquier función recursiva parcial. Esto asegurara (suponiendo que la tesis de Church-

Turing es verdadera) que, mientras un lenguaje de programación cuente con las características de nuestro lenguaje

esencial, permitirá expresar una solución para cualquier problema que pueda resolverse de manera algorítmica.

8.1 El lenguaje de la lógica proposicional

El alfabeto de la lógica de proposiciones debe proporcionar los símbolos necesarios para representar

proposiciones sobre el mundo. Como el número de proposiciones que pueden manejarse en un mismo

razonamiento no está limitado, debe proveer un número infinito de letras proposicionales.

Alfabeto de la lógica de proposiciones. El alfabeto A de la Lógica de proposiciones consta de los siguientes

elementos: infinitas letras proposicionales: , símbolos lógicos: constantes ( ), conectiva monaria

( ) y conectivas binarias ( ) y dos símbolos auxiliares de puntuación: paréntesis izquierdo’(’ y derecho

’)’. Así,

En las exposiciones teóricas, el número de letras proposicionales que se consideran simultáneamente es pequeño

(por ejemplo, de a ). En estos casos se suelen notar informalmente con las últimas letras del alfabeto latino:

A las expresiones aceptables se las denominará fórmulas o expresiones bien formadas. El

conjunto (infinito) que incluye todas estas fórmulas (y nada más) es el lenguaje de la lógica de proposiciones, que

notaremos como .

El conjunto , que contiene todas las expresiones aceptables en nuestro lenguaje (y sólo éstas), es el menor

de los conjuntos que verifica que todas las fórmulas atómicas pertenecen a ; si la expresión entonces

; y si las expresiones entonces .

Un lenguaje de programación esencial. Dado que nuestro lenguaje de programación esencial se usara para

calcular funciones recursivas parciales, el único tipo de dato que se requiere es el entero no negativo (como ya

61

hemos señalado, en un ordenador digital moderno todo dato se representa como un entero no negativo, aunque los

lenguajes de alto nivel puedan disfrazar esta realidad). Por esta razón, nuestro lenguaje de programación esencial

no necesita enunciados de declaración de tipo, sino que los identificadores se declaran automáticamente como de

tipo entero no negativo con solo aparecer una vez en un programa. Para su representación se ha utilizado el

lenguaje C, como puede ser cualquier lenguaje existente. El lenguaje contendrá los dos enunciados de asignación

siguientes:

incr nombre; y decr nombre;

El primero incrementa en uno el valor asignado al identificador nombre, mientras que el segundo lo decrementa

en uno, a menos que el valor a decrementar sea 0, en cuyo caso permanece con dicho valor. El lenguaje se

completa entonces con una estructura de control formada por los dos siguientes enunciados:

while nombre 6= 0 do

...

end;

Esta estructura indica que es necesario repetir los enunciados que se encuentren entre while y end mientras el

valor asignado al identificador nombre no sea cero. Lenguaje de programación el lenguaje de programación

se denomina (por programming language while, es decir, lenguaje de programación con repeticiones

while). Ver capitulo 7 donde se aplica el concepto. Este es entonces nuestro lenguaje de programación esencial.

Efectivamente, es tan sencillo que nuestro primer objetivo sería el de incorporar algunos enunciados más potentes,

que puedan simularse con secuencias de enunciados esenciales. Una vez hecho esto, podremos utilizar los

enunciados adicionales para escribir programas más claros. Más concretamente, adoptaremos la sintaxis: clear

nombre; como versión abreviada de la secuencia:

while nombre 6 0 do

decr nombre;

end;

cuyo efecto es asignar el valor 0 al identificador nombre. Además, utilizaremos

nombre1 nombre2;

para representar el siguiente segmento de programa:

clear aux;

clear nombre1;

while nombre2 6= 0 do

62

incr aux;

decr nombre2;

end;

while aux 6= 0 do

incr nombre1;

incr nombre2;

decr aux;

end;

el cual asigna el valor de nombre2 al identificador nombre1, asignándolo primero a la variable auxiliar aux, y

Después reasignándolo tanto a nombre1 como a nombre2. Obsérvese que el esfuerzo que implica el uso de aux

permite evitar el efecto colateral de destruir la asignación original de nombre2.

Recursiva parcial implica programable con lo esencial. La siguiente tarea sería la de mostrar que para

cualquier función recursiva parcial existe un algoritmo que calcula dicha función, el cual puede expresarse con

nuestro sencillo lenguaje de programación esencial. Para ello, estableceremos la convención de que para calcular

una función de a escribiremos un programa con los identificadores para contener los valores

de entrada, y con para almacenar los valores de salida. Con nuestro sencillo lenguaje esencial es fácil

expresar los programas que corresponden al cálculo de las funciones iniciales:

La función o función cero está representada por:

clear ;

La función o función sucesor se representa mediante:

;

incr ;

Y las funciones de proyección j pueden calcularse como sigue:

;

Seguidamente al centrar la atención sobre la técnica de construcción de los algoritmos correspondientes a las

funciones recursivas parciales:

Combinación. Si y son dos programas que calculan las funciones parciales y ,

respectivamente, entonces la función se puede calcular concatenando al final del programa ,

modificando y para que asignen sus salidas a los identificadores apropiados ( debe asignar su salida

63

a a la vez que asigna su salida a ) y ajustando para que no destruya los valores de

entrada antes de que pueda utilizarlos.

Por supuesto, tanto aquí como en los casos que se presentan más adelante, suponemos que los programas en

cuestión no tienen nombres de variables auxiliares comunes que pudieran ocasionar efectos colaterales. En este

caso, si los tuvieran, siempre podríamos cambiarlos para obtener espacios de nombres distintos, haciendo que

todos los identificadores del programa estuvieran precedidos por la letra y todos los del programa por la

letra

Composición. Si y son dos programas que calculan las funciones parciales y ,

respectivamente, entonces la función g ∘ f se puede calcular concatenando al final del programa y ajustando

los identificadores de salida de para que vayan de acuerdo con los identificadores de entrada de .

Recursividad primitiva. Ahora supongamos que el programa calcula la función parcial , el

programa calcula y, usando recursividad primitiva, la función se define como:

Entonces se puede calcular con el siguiente programa:

G

aux ;

clear ;

while aux 6= 0 do

...

.

H

incr ;

decr aux;

end;

donde, sin pérdida de generalidad, podemos suponer que y no tienen efectos secundarios indeseables.

Minimalizacion. Si es un programa que calcula la función parcial , entonces podemos producir un

programa que calcule como sigue:

64

clear ;

G

while do

incr ;

G

end;

;

Este programa lleva a cabo dicha tarea calculando hasta que produce una salida

cero para un cierto valor , almacenado realmente en , el cual constituirá el valor final de salida del

programa. Obsérvese que se puede diseñar para que no altere las asignaciones originales de sus variables de

entrada.

Hasta aquí se ha mostrado entonces que cualquier función recursiva parcial puede calcularse por medio de un

programa escrito en nuestro lenguaje de programación esencial. Por tanto, de acuerdo con la tesis de Church-

Turing, sabemos que cualquier lenguaje que proporcione el tipo entero no negativo y la capacidad para

incrementar un valor, decrementarlo y ejecutar un ciclo while, tendría el poder expresivo suficiente para plantear

la solución de cualquier problema que tenga una solución algorítmica. Todas las características adicionales de un

lenguaje representan simplemente conveniencias que facilitan las labores de programación.

Programable con lo esencial implica recursiva parcial. Después de haber descubierto el sorprendente poder de

nuestro sencillo lenguaje, se podría pensar que ofrece un medio para calcular algo más que las funciones

recursivas parciales. Por supuesto, si esta conjetura fuera verdadera, contradirá la tesis de Church-Turing ya que

obtendríamos un método para calcular una clase de funciones mayor que la de las funciones recursivas parciales

(que son las computables por máquinas de Turing). Por tanto, efectivamente, no constituye ninguna sorpresa el

encontrar que cualquier cálculo expresado en nuestro sencillo lenguaje de programación puede modelarse por

medio de una función recursiva parcial. La estrategia para demostrar esta afirmación consiste en aplicar

razonamientos inductivos sobre el posible número de enunciados de un programa.

Si nos centramos en la máquina de Turing, en la que no existen estas limitaciones, podremos entender mejor la

idea básica de que algún dispositivo de computación será capaz de hacerlo, si no hoy día, sí en un futuro. Se

proporcionara una descripción formal de que existe un problema de las máquinas de Turing que ninguna de ellas

puede resolver. Las máquinas de Turing pueden simular computadoras reales, incluso a aquellas que no tienen las

limitaciones que sabemos que actualmente tienen, por lo que dispondremos de un argumento riguroso de que el

siguiente problema: ¿Se acepta esta máquina de Turing a sí misma (su propia codificación) como entrada? no

65

puede ser resuelto por una computadora, independientemente de lo generosamente que se relajen las limitaciones

prácticas. Para el sistema lógico proposicional nuestro codificación es binaria, y por tal motivo la generación de la

cinta con la cadena de unos y ceros tiene un significado, y lo más básico es expresarlos en términos lógicos: si

está o no en operación, está o no está disponible, existe capacidad o no, se cuenta con inventario o no etc. Lo no

expresado de forma binario se codificara con un sistema lógico cambinacional que interpretara la MT. Este

concepto se desarrolla en el procedimiento de diseño de algoritmos combinacionales.

Se divide entonces los problemas que puede resolver una máquina de Turing en dos categorías: aquellos que

tienen un algoritmo (es decir, una máquina de Turing que se detiene en función de si acepta o no su entrada), y

aquéllos que sólo son resueltos por máquinas de Turing que pueden seguir ejecutándose para entradas que no

aceptan. Esta última forma de aceptación es problemática, ya que sea cual sea el tiempo que la esté en

ejecución, no podemos saber si la entrada es aceptada o no. Por tanto, vamos a centrarnos en las técnicas que

demuestran que los problemas son “indecidibles”, es decir, que no tienen ningún algoritmo, independientemente

de si son o no aceptados por una máquina de Turing que no se detiene para algunas entradas. (Carlos Guillén,

2005)

Describiré que el siguiente problema es indecidible: ¿Acepta esta máquina de Turing esta entrada?

A continuación, se aplicara el resultado obtenido acerca de la indecidibilidad a una serie de problemas

indecidibles. Todos los problemas no triviales acerca del lenguaje aceptado por una máquina de Turing son

indecidibles, así como una serie de problemas que no tienen nada que ver con las máquinas de Turing, los

programas o las computadoras. En capitulo 6, se explica detalladamente el funcionamiento de la máquina de

Turing., y por el momento nos interesa determinar que el lenguaje a utilizar lo acepte.

El término “recursivamente enumerable” recuerda la misma familia de conceptos. Una función podría enumerar

todos los elementos de un lenguaje en un cierto orden. Los lenguajes que pueden enumerar sus elementos en

cierto orden son los mismos que los lenguajes aceptados por algunas , aunque dichas pueden no detenerse

nunca para las entradas que no aceptan.

8.2 Lenguajes recursivos

Decimos que un lenguaje es recursivo si para una máquina de Turing tal que:

1. Si pertenece a , entonces acepta (y por tanto se para).

2. Si no pertenece a , entonces termina parándose, aunque nunca llega a un estado de aceptación.

66

Una de este tipo se corresponde con nuestro concepto informal de “algoritmo”, una secuencia bien definida

de pasos que siempre termina y genera una respuesta. Si pensamos en el lenguaje como en un “problema”, lo

que será frecuente, entonces se dice que el problema es decidible si es un lenguaje recursivo, y se dice que es

indecidible si no es un lenguaje recursivo.

La existencia o no existencia de un algoritmo para resolver un problema a menudo tiene más importancia que la

existencia de una que resuelva el problema. Como se ha mencionado anteriormente, las máquinas de Turing

que no garantizan la parada no pueden proporcionarnos la suficiente información como para concluir que una

cadena no pertenece al lenguaje, por lo que en cierto sentido no “resuelven el problema”. Por tanto, dividir los

problemas o los lenguajes entre decidibles (aquellos que se resuelven mediante un algoritmo) e indecidibles, a

menudo es más importante que la división entre lenguajes recursivamente enumerables (aquellos para los que

existen máquinas de Turing de alguna clase) y lenguajes no recursivamente enumerables (aquellos para los que no

existe ninguna ). La figura 18 muestra la relación entre estas tres clases de lenguajes:

1. Los lenguajes recursivos.

2. Los lenguajes que son recursivamente enumerables pero no recursivos.

3. Los lenguajes no recursivamente enumerables

El lenguaje no lo hemos colocado apropiadamente y también el lenguaje o “lenguaje universal”, que

demostraremos en breve que no es recursivo, aunque sí .

Complementarios de los lenguajes recursivos y . Una potente herramienta para comprobar qué lenguajes

están dentro del segundo círculo de la figura 18 (es decir, que son , pero no recursivos) es el complementario

del lenguaje. Demostraremos que los lenguajes recursivos son cerrados para la complementación. Por tanto, si un

lenguaje es , pero , el complementario de , no es , entonces sabemos que no puede ser recursivo. Si

fuera recursivo, entonces también sería recursivo y, por tanto, seguramente . Ahora vamos a demostrar esta

importante propiedad de clausura de los lenguajes recursivos. Ver anexo Teorema 17.

Figura 1. Relación entre los lenguajes RE y no RE

67

Recursivo

RE pero

no recursivo

No RE

. Ld

. Lu

Fuente: Autor

El lenguaje universal. Se explicara informalmente cómo podría emplearse una máquina de Turing para simular

una computadora cargada con un programa arbitrario. Esto quiere decir que una única máquina de Turing se

puede emplear como una “computadora que ejecuta un programa almacenado”, que toma el programa y los datos

de una o más cintas en las que se coloque la entrada. Vamos a repetir esta idea con la formalidad adicional de que

el programa almacenado también es una representación de una máquina de Turing.

Se define , el lenguaje universal, para que sea el conjunto de cadenas binarias que codifican, utilizando la

notación, un par , donde es una con el alfabeto de entrada binario y es una cadena de tal

que pertenece a Es decir, es el conjunto de cadenas que representan a una y una entrada aceptada

por dicha . Se mostrara que existe una , a menudo conocida como máquina de Turing universal, tal

que . Puesto que la entrada a es una cadena binaria, es en realidad una de la lista de máquinas de

Turing con entrada binaria que se ha desarrollado.

Es más fácil describir como una máquina de Turing de varias cintas. La aplicación de una de tres cintas se

da en el nivel II, cuando obtengamos en la salida de la que representa cada centro de trabajo. Las cintas

necesarias serán para cada una de los recursos declarados en cada clausula2 en la formula lógica proposicional que

igualmente son que se ejecutan con un sistema lógico secuencial. En el caso de , las transiciones de se

almacenan inicialmente en la primera cinta, junto con la cadena . Una segunda cinta se utilizará para almacenar

la cinta simulada de , utilizando el mismo formato que para el código de . Es decir, representará el símbolo

de cinta de y los símbolos de cinta se separarán mediante un único 1. La tercera cinta de almacena el

estado de , con el estado representado por ceros.

El funcionamiento de puede resumirse como sigue:

2 Cláusula de Horn. En lógica proposicional, una fórmula lógica es una cláusula de Horn si es una cláusula (disyunción de literales) con, como máximo, un

literal positivo. Se llaman así por el lógico Alfred Horn, el primero en señalar la importancia de estas cláusulas en 1951.

68

1. Al examinar la entrada para asegurar que el código para es un código válido para una . Si no lo es, se

para sin aceptar. Puesto que se supone que los códigos no válidos representan la sin ningún movimiento y

que tal no acepta ninguna entrada, esta acción es correcta.

2. Inicializar la segunda cinta para que contenga la entrada , en su forma codificada. Es decir, para cada 0 de ,

se incluye 10 en la segunda cinta y para cada 1 de , se incluye 100 en la misma. Observe que los espacios en

blanco de la cinta simulada de , que están representados por 1000, no aparecerán en dicha cinta; todas las

casillas situadas más allá de las que utiliza almacenarán los espacios en blanco de . Sin embargo, sabe

que, si busca un símbolo simulado de y encuentra su propio espacio en blanco, tiene que reemplazar dicho

espacio en blanco por la secuencia 1000 para simular el espacio en blanco de .

3. Colocar 0, el estado inicial de , en la tercera cinta y mover la cabeza de la segunda cinta de a la primera

casilla simulada.

4. Para simular un movimiento de , busca en la primera cinta una transición tal que sea el

estado de la cinta 3 y sea el símbolo de cinta de que comienza en la posición de la cinta 2 señalada por la

cabeza de . Esta transición determina la siguiente acción de . tiene que:

a. Cambiar el contenido de la cinta 3 a ; es decir, simular el cambio de estado de Para ello, en

primer lugar, cambia todos los ceros de la cinta 3 por espacios en blanco, y luego copia de la

cinta 1 a la cinta 3.

b. Reemplazar 0j de la cinta 2 por ; es decir, cambiar el símbolo de cinta de . Si se necesita más o

menos espacio (es decir, ), utiliza la cinta auxiliar y la técnica de desplazamiento para gestionar

la utilización del espacio.

c. Mover la cabeza de la cinta 2 a la posición en la que se encuentre el siguiente 1 hacia la izquierda o

hacia la derecha, respectivamente, dependiendo de si (movimiento a la izquierda) o

(movimiento a la derecha). Así, simula los movimientos de hacia la izquierda o hacia la derecha.

5. Si no dispone de ninguna transición que corresponda al estado y símbolo de cinta simulados, entonces en el

paso (4), no se encontrará ninguna transición. Por tanto, se para en la configuración simulada y deberá

hacer lo mismo.

6. Si entra en un estado de aceptación, entonces acepta.

De esta forma, simula sobre . acepta el par codificado si y sólo si acepta .

Indecidibilidad del lenguaje universal. Ahora se aborda un lenguaje que es pero no recursivo: el lenguaje .

Saber que es indecidible (es decir, que no es un lenguaje recursivo) es mucho más valioso que nuestro anterior

descubrimiento de que no es . La razón es que la reducción de a otro problema puede emplearse para

demostrar que no existe ningún algoritmo para resolver , independientemente de si es o no es . Sin

embargo, la reducción de a sólo es posible si no es , por lo que no se puede utilizar para demostrar la

69

indecidibilidad de aquellos problemas que son pero no son recursivos. Por el contrario, si deseamos demostrar

que un problema no es , entonces sólo podemos utilizar , ya que no es útil en este caso puesto que es .

Una universal más eficiente. Una simulación eficiente de por parte de , que no exigiese tener que

desplazar los símbolos de la cinta, pasaría por, en primer lugar, que determinase el número de símbolos de cinta

que utiliza. Si existen entre símbolos, podría utilizar un código binario de bits para

representar de forma unívoca los diferentes símbolos de cinta. Las casillas de la cinta de podrían simularse

mediante casillas de la cinta de . Para hacer las cosas todavía más fáciles, podría reescribir las transiciones

de para utilizar un código binario de longitud fija en lugar del código unario de longitud variable que se ha

utilizado aquí.

El problema de la parada. A menudo se dice que el problema de la parada de las máquinas de Turing es similar

al problema (un problema que es pero no recursivo). De hecho, la máquina de Turing original de A. .

Turing acepta por parada, no por estado final. Se podría definir para la como el conjunto de entradas

tales que se detiene para la entrada dada, independientemente de si acepta o no w. Entonces, el

problema de la parada es el conjunto de pares tales que pertenece a Este problema/lenguaje es

otro caso de un problema que es pero no recursivo.

¿Por qué los problemas y sus complementarios son diferentes?. La intuición nos dice que un problema y su

complementario realmente son el mismo problema. Para resolver uno de ellos, podemos utilizar un algoritmo para

el otro y, en el último paso, complementar la salida: indicar “sí” en lugar de “no”, y viceversa. Esta idea intuitiva

es correcta siempre y cuando el problema y su complementario sean recursivos.

Sin embargo, existen otras dos posibilidades. La primera de ellas es que ni el problema ni su complementario son

. En este caso, ningún tipo de puede resolver ninguno de ellos, por lo que en cierto sentido de nuevo los

dos son similares. Sin embargo, el caso interesante, tipificado por y , es cuando uno es y el otro es

.

Para el lenguaje que es , podemos diseñar una que tome una entrada y busque una razón por la que

pertenezca al lenguaje. Así, para , dada una como entrada, hacemos que nuestra T busque cadenas

que la acepte, y tan pronto como encuentre una, aceptamos . Si es una con un lenguaje vacío,

nunca sabremos con certeza que no pertenece a , pero nunca aceptaremos , y ésta es la repuesta correcta

que proporciona la nueva .

Por otro lado, para el problema complementario , el que es no-RE, no existe ninguna manera de aceptar todas

sus cadenas. Suponga que tenemos una cadena que es una cuyo lenguaje es el lenguaje vacío. Se puede

probar las entradas aplicadas a la , y es posible que ni siquiera encontremos una que acepte, y aún así

70

nunca podremos estar seguros de que no existe alguna entrada que todavía no haya sido comprobada y que sea

aceptada por esta . Por tanto, puede no ser nunca aceptada, incluso aunque tuviera que serlo.

Lenguaje no recursivamente enumerable. Un lenguaje es recursivamente enumerable si ) para

alguna máquina de Turing . Los lenguajes “recursivos” o “decidibles” que no sólo no son recursivamente

enumerables, sino que son aceptados por una que siempre se detiene, independientemente de si acepta o no.

Nuestro objetivo a largo plazo es demostrar la indecibilidad del lenguaje que consta de pares tales que:

1. es una máquina de Turing (codificada adecuadamente en binario) con el alfabeto de entrada

2. es una cadena de ceros y unos, y

3. acepta la entrada .

Si este problema con entradas restringidas al alfabeto binario es indecidible, entonces con toda probabilidad el

problema más general, en el que la puede utilizar cualquier alfabeto, será indecidible.

El primer paso consiste en enunciar este problema como una cuestión acerca de la pertenencia a un determinado

lenguaje. Por tanto, tenemos que determinar una codificación para las máquinas de Turing que sólo utilizan ,

independientemente de cuántos estados tenga la . Una vez que dispongamos de esta codificación, podremos

tratar cualquier cadena binaria como si fuera una máquina de Turing. Si la cadena no es una representación bien

formada de una , podemos interpretarlo como una representación de un sin movimientos. Por tanto,

podemos pensar que cualquier cadena binaria representa una .

Un objetivo intermedio, implica al lenguaje , el “lenguaje de diagonalización”, formado por todas aquellas

cadenas tales que la representada por no acepta la entrada Se demostrara que no es aceptado por

ninguna máquina de (Turing, 1936). Recuerde que demostrando que no existe ninguna máquina de Turing para un

lenguaje, estamos demostrando algo aún más restrictivo que el hecho de que el lenguaje sea indecidible (es decir,

que no existe ningún algoritmo, o ninguna que siempre se pare).

El lenguaje desempeña un papel análogo al programa hipotético , que imprime cuando su salida no imprimía

hola, mundo al proporcionarse él mismo como entrada.

Dicho de forma más precisa, igual que no puede existir porque su respuesta al proporcionarse él mismo como

entrada lleva a una paradoja, no puede ser aceptado por una máquina de Turing, porque si lo fuera, entonces

dicha máquina de Turing tendría que estar en desacuerdo consigo misma cuando se le proporcionara su propio

código como entrada. (Sara Baase, 2002)

Enumeración de cadenas binarias. A continuación, se necesita asignar enteros a todas las cadenas binarias, de

modo que cada cadena se corresponda con un entero y que cada entero se corresponda con una cadena. Si es

71

una cadena binaria, se trata como el entero binario Entonces se considera que es la -ésima cadena. Es

decir, es la primera cadena, 0 es la segunda, 1 la tercera, 00 la cuarta, 01 la quinta, etc. De forma equivalente, las

cadenas se ordenan de acuerdo con la longitud, y las cadenas de la misma longitud se ordenan alfabéticamente.

De aquí en adelante, se denominara a la cadena -ésima.

Códigos para las máquinas de Turing. Nuestro siguiente objetivo es definir un código binario para las máquinas

de Turing de modo que cada con el alfabeto de entrada pueda interpretarse como una cadena binaria.

Puesto que ya ha visto cómo enumerar cadenas binarias, se dispone entonces de un medio de identificación de las

máquinas de Turing mediante enteros, y se podria hablar de “la -ésima máquina de Turing, ”. Para representar

una como una cadena binaria, primero se tiene que asignar números enteros al

estado, los símbolos de cinta y las direcciones y .

Se supone que los estados son para algún . El estado inicial siempre será y será el único estado

de aceptación. Observe que, dado que se puede suponer que la se para cuando entra en un estado de

aceptación, nunca existe la necesidad de que haya más de un estado de aceptación.

Suponer que los símbolos de cinta son para algún . siempre será el símbolo 0, será el 1 y

será , el espacio en blanco. No obstante, pueden asignarse otros símbolos de cinta a los restantes enteros de

forma arbitraria. Al denominar la dirección (izquierda) y a la dirección (derecha) .

Dado que el orden en que se asignan los enteros a los estados y símbolos de cinta de cada puede ser

diferente, existirá más de una codificación para cada Sin embargo, este hecho no es importante, ya que se va a

demostrar que ninguna codificación puede representar una tal que .

Al asignar un entero a cada estado, símbolo y dirección, se puede codificar la función de transición Suponer

que una regla de transición es para los valores enteros y . Codificar esta cadena

mediante la cadena . Observe que, dado que y valen, como mínimo, uno, no existen

subcadenas de dos o más unos consecutivos en el código de una única transición.

Un código para la completa consta de todos los códigos correspondientes a las transiciones, en un cierto

orden, separados por pares de unos:

donde cada una de las corresponde al código de una transición de . En la teoría de autómatas la es una

representación de este mismo, y lo abordare no desde el punto de vista computacional sino como un sistema

lógico secuencial asíncrono y síncrono y defino la función de transición. Ver sección 5.3.

El lenguaje de diagonalización. Se han codificado las máquinas de Turing, por lo que ahora se tiene un concepto

concreto de , la “máquina de Turing -ésima”: es aquella cuyo código es , la cadena binaria -ésima.

72

Muchos enteros no se corresponden con ninguna . Por ejemplo, 11001 no comienza por 0, y

0010111010010100 tiene tres unos consecutivos. Si no es un código válido de , interpretar que es una

con un estado y ninguna transición. Es decir, para dichos valores de , es una máquina de Turing que se

detiene de forma inmediata para cualquier entrada. Por tanto, ) es si no es un código válido de la .

Ahora se esta en condición de establecer una explicación extremadamente importante. El lenguaje , el lenguaje

de diagonalización, es el conjunto de cadenas tal que no pertenece a ). Es decir, consta de todas las

cadenas tales que la , cuyo código es , no acepta cuando se proporciona como entrada.

La razón por la que se denomina lenguaje de “diagonalización” puede verse fijándose en la tabla.

Tabla 7. Tabla que representa la aceptación de cadenas por máquinas de Turing.

1 2 3 4 5 …

1 0 1 1 0 0 0 …

2 1 1 0 0 1 1 …

3 0 0 1 1 0 1 …

4 0 0 0 1 1 0 …

5 1 0 1 0 1 1 …

. . . . . .

Esta tabla indica para todo y , si la acepta o no la cadena de entrada ; 1 signfica que “sí la acepta” y 0

indica que “no la acepta”.1 La fila -ésima puede intrepretarse como el vector característico del lenguaje );

es decir, los unos de esta fila indican las cadenas que pertenecen a este lenguaje.

Los valores de la diagonal indican si acepta . Para construir , se complementa la diagonal de la tabla 4. Si

la tabla 4 fuera la tabla correcta, entonces la diagonal complementada comenzaría por 1,0,0,0, . . . Por tanto,

contendría , no contendría hasta , que son 0, 1 y 00, etc.

El proceso que consiste en complementar la diagonal para construir el vector característico de un lenguaje, que no

puede ser el lenguaje que aparece en ninguna de las filas, se denomina diagonalización. Este proceso funciona

porque el complementario de la diagonal es en sí mismo un vector característico que describe la pertenencia a un

lenguaje, que se denomina . Este vector característico difiere en alguna columna de todas las filas de la tabla

mostrada en la tabla 4. Por tanto, el complementario de la diagonal no puede ser el vector característico de

ninguna máquina de Turing.

73

Demostración de que no es recursivamente enumerable. Siguiendo la intuición anterior acerca de los

vectores característicos y la diagonal, se demuestra formalmente un resultado fundamental sobre las máquinas de

Turing: no existe ninguna máquina de Turing que acepte el lenguaje . Ver anexo Teorema 16.

Un problema indecidible recursivamente enumerable. Hasta aquí, se ha examinado un problema (el lenguaje

de diagonalización ) que no es aceptado por una máquina de Turing. El siguiente objetivo es depurar la

estructura de los lenguajes recursivamente enumerables (aquellos que son aceptados por las ) y

clasificarlos dentro de dos clases. Una clase, la que corresponde a lo que normalmente se denomina algoritmo,

dispone de una que no sólo reconoce el lenguaje, sino que también informa de si una cadena de entrada no

pertenece al lenguaje. Una máquina de (Turing, 1936) así siempre termina parándose, independientemente de si

llega a alcanzar o no un estado de aceptación.

La segunda clase de lenguajes está formada por aquellos lenguajes que no son aceptados por ninguna máquina

de Turing que garantice la parada en todos los casos. Estos lenguajes son aceptados de una forma poco adecuada;

si la entrada pertenece al lenguaje, terminará aceptándola, pero si la entrada no pertenece al lenguaje, entonces la

máquina de Turing continuará ejecutándose indefinidamente y nunca se podrá estar seguro de que dicha entrada

no será finalmente aceptada. Este tipo de lenguaje es el conjunto de pares codificados tales que la

acepta la entrada .

Máquinas de Turing que aceptan el lenguaje vacío. Como casos de reducciones que implican máquinas de

Turing, se va a examinar dos lenguajes denominados y . Cada uno de ellos consta de cadenas binarias. Si

es una cadena binaria, entonces representa a una cierta , de la enumeración de las máquinas de Turing.

Si , es decir, no acepta ninguna entrada, entonces pertenece a . Por tanto, es el lenguaje

formado por todas aquellas codificaciones de cuyo lenguaje es el lenguaje vacío. Por el contrario, si no

es el lenguaje vacío, entonces pertenece a . Por tanto, es el lenguaje que consta de todos los códigos de

las máquinas de Turing que aceptan al menos una cadena de entrada.

De aquí en adelante, resultará conveniente interpretar las cadenas como las máquinas de Turing que representan.

Así, se puede definir los dos lenguajes mencionados como sigue:

Observe que y son lenguajes sobre el alfabeto binario y que son complementarios entre sí. Veremos

que es el más “sencillo” de los dos y es pero no recursivo. Por el contrario, es .

74

es recursivamente enumerable. Demostración. Hay que demostrar que existe una que acepta . Para

ello, lo más sencillo es describir una no determinista , cuyo esquema se muestra en la figura 19. De acuerdo

con el teorema, puede convertirse en una determinista.

Figura 2. Construcción de un MT no determinística que acepta

Aceptar Aceptar

Cadena

w

Mi

M para Lne

U

Fuente: Autor

El funcionamiento de es el siguiente.

1. toma como entrada el código de una .

2. Utilizando su capacidad no determinista, prueba con una entrada que podría aceptar.

3. comprueba si acepta . Para esta parte del proceso, puede simular a la universal que acepta

Lu.

4. Si acepta w, entonces acepta su propia entrada, que es .

De esta forma, si acepta aunque sea una sola cadena, terminaría encontrándola (entre otras muchas, por

supuesto), y aceptaría . Sin embargo, si entonces ninguna cadena sería aceptada por , por lo que

no aceptará . Por tanto .

El siguiente paso consiste en demostrar que no es recursivo. Para ello, se reduce a . Es decir, describir

un algoritmo que transforme una entrada en una salida , el código de otra máquina de Turing, tal que

pertenezca a si y sólo si no es el lenguaje vacío. Es decir, acepta si y sólo si acepta al menos

una cadena. El truco está en que ignora su entrada, en lugar de simular para la entrada . Si acepta,

entonces acepta su propia entrada; por tanto, la aceptación de por parte de es equivalente a que no

sea el lenguaje vacío. Si fuera recursivo, entonces se tendría un algoritmo para determinar si acepta o no la

cadena w: construir y ver si

no es recursivo.

Figura 3. Esquema de construida a partir de : acepta una entrada arbitraria si y sólo si acepta .

75

Aceptar Aceptar

w

M’

U

Fuente: Autor

Se seguirá la misma línea que en la demostración anterior. Al diseñar un algoritmo que convierta una entrada, que

es un par codificado en binario en una tal que si y sólo si acepta la entrada . La

construcción de se muestra en la figura 20. Como veremos, si no acepta , entonces no acepta ninguna de

sus entradas; es decir . Sin embargo, si acepta , entonces acepta todas las entradas y, por tanto,

no será .

se diseña como sigue: ignora su propia entrada . En su lugar, reemplaza su entrada por la cadena que

representa la y la cadena de entrada Puesto que está diseñada para un par específico cuya

longitud será , se puede construir para disponer de una secuencia de estados , donde es el

estado inicial.

En el estado para escribe el -ésimo bit del código de pasa al estado y se

mueve hacia la derecha.

En el estado , se mueve hacia la derecha, si fuera necesario, reemplazando los símbolos no blancos (que

corresponderán a la cola de , si dicha entrada a tiene una longitud mayor que ) por espacios en blanco.

Cuando encuentra un espacio en blanco estando en el estado , utiliza una colección similar de estados para

volver a posicionar su cabeza en el extremo izquierdo de la cinta. Ahora, utilizando estados adicionales, simula

una universal en su cinta actual. Si acepta, entonces acepta. Si nunca acepta, entonces tampoco

aceptará nunca.

La anterior descripción de debería bastar para convencerse de que se podría diseñar una máquina de Turing que

transformara el código de y la cadena en el código correspondiente a . Es decir, existe un algoritmo que

permite llevar a cabo la reducción de a . Ver también que si acepta , entonces aceptará cualquier

entrada que estuviera originalmente en su cinta. El hecho de que sea ignorada es irrelevante; la descripción de

aceptación por una establece que lo que la acepta es lo que haya en su cinta antes de comenzar a operar.

Por tanto, si acepta , entonces el código correspondiente a pertenece a

76

Inversamente, si no acepta , entonces nunca acepta, independientemente de cuál sea su entrada. Por tanto,

en este caso, el código para no pertenece a . Al reducir satisfactoriamente a aplicando el algoritmo

que construye a partir de y; se puede concluir que, dado que no es recursivo, tampoco lo es.

La existencia de esta reducción es suficiente para completar la demostración. Sin embargo, para ilustrar la

influencia de esta reducción, se va a llevar este argumento un paso más allá. Si fuera recursivo, entonces se

podría desarrollar un algoritmo para de la forma siguiente:

Al convertir en la como anteriormente. Se utiliza un algoritmo hipotético para para determinar si

resulta o no que ,. En caso afirmativo, decir que no acepta ; y si , entonces decir que

acepta .

Según el teorema, saber que no existe tal algoritmo para , y se ha llegado a una contradicción de la hipótesis

que establecía que era recursivo, y concluir que no es recursivo. Ahora ya se conoce el estado de . Si Le

fuera , entonces por el teorema, tanto él como serían recursivos. De acuerdo con el teorema, no es

recursivo, se puede concluir que: no es

77

ANEXO 9. Lenguajes recursivamente numerables y recursivos

Un lenguaje es recursivamente numerable si y sólo si existe una que lo reconoce. Es decir, si es el conjunto de

todos los lenguajes (cada uno integrado por cadenas finitas de símbolos pertenecientes a un alfabeto universal ),

sólo los lenguajes recursivamente numerables de son reconocibles por una (por esto es que a los problemas de

decisión asociados se los conoce como computables). La clase de los lenguajes recursivamente numerables se

denomina (por recursively enumerables languages). El nombre se debe a que las cadenas de estos lenguajes se

pueden enumerar. De esta manera, dado , si es una tal que , se cumple para toda cadena

de que:

a. Si , entonces a partir de se detiene en su estado .

b. Si , entonces a partir de se detiene en su estado o no se detiene.

Se va a probar después que no todos los lenguajes son recursivamente numerables, y que sólo algunos tienen la

propiedad de que las que los reconocen se detienen siempre. Considerando este último caso, se define que un

lenguaje es recursivo si y sólo si existe una que lo reconoce y que se detiene cualquiera sea su entrada. La

clase de los lenguajes recursivos se denomina . A los problemas de decisión asociados se los conoce como

decidibles, porque las que los resuelven pueden justamente decidir, cualquiera sea la instancia, si es positiva o

negativa. Ahora, dado , si es una tal que , se cumple para toda cadena de que:

a. Si , entonces a partir de se detiene en su estado .

b. Si , entonces a partir de se detiene en su estado .

Se cumple que . Al probar entre esta clase y la que viene que , es decir que no todos

los problemas computables son decidibles, y que no todos los problemas son computables (las fronteras de y

determinan los límites de la decidibilidad y la computabilidad, respectivamente). Esto se ilustra en la siguiente

figura 74, que presenta una primera versión de la jerarquía de la computabilidad:

Figura 4. Jerarquia de computabilidad

R

RE

78

Fuente: Autor

En los dos teoremas, se presentan algunas propiedades de clausura de las clases y Algunos de estos

resultados se utilizan en la prueba de correctitud de la jerarquía planteada, al tiempo que sus demostraciones

permiten continuar con la ejercitación en la construcción de , ahora utilizando notación algorítmica en lugar de

funciones de transición, e incorporando casos de composición de , técnica que se seguirá empleando en las

próximas clases.

Algunas propiedades de clausura de la clase . Considerando las operaciones de complemento, intersección,

unión y concatenación de lenguajes, se cumple que la clase es cerrada con respecto a todas ellas. Al probar

primeramente que la clase es cerrada con respecto al complemento. Dado un lenguaje , su lenguaje

complemento es Se demuestra a continuación que si , entonces también

.

Dado un lenguaje recursivo , sea una que lo acepta y se detiene siempre, es decir a partir de cualquier

entrada. Se va a construir una que acepta y se detiene siempre, de la siguiente manera: dada una

entrada , si se detiene en , entonces se detiene en , y viceversa. La figura 75 siguiente ilustra esta idea:

Figura 5. que acepta

Mw Si

No

Si

No

M c

Fuente: Autor

Construcción de la Si Γ δ , , ), entonces con y idénticas

salvo en la aceptación y rechazo. Para todo estado de , todo par de símbolos y de , y todo movimiento

del conjunto se define:

a. Si entonces

b. Si d), entonces

Prueba de que se detiene siempre.

a. con entrada , se detiene en con entrada , se detiene en .

79

b. con entrada , se detiene en con entrada , se detiene en .

Prueba de

con entrada se detiene en con entrada , se detiene en

Esta es una típica prueba por construcción de que un lenguaje es recursivo. Se construye una , y se prueba

que se detiene siempre y acepta . La prueba por construcción de que un lenguaje es recursivamente

numerable, en cambio, requiere solamente la construcción de una y la prueba de que acepta .

La clase también es cerrada con respecto a las operaciones de intersección y unión de lenguajes. Es decir, si

entonces . Al probar el caso de la intersección. El caso de la unión

queda como ejercicio.

Sean una que acepta y se detiene siempre, y una que acepta y se detiene siempre. Se va a

construir una que acepta y se detiene siempre, con las siguientes características. simula primero

y luego . Dada una entrada , si se detiene en su estado , entonces directamente se detiene en su

estado .

En cambio, si se detiene en su estado , entonces con la misma entrada , la simula , y se detiene en

su estado (respectivamente ) si se detiene en su estado (respectivamente ). La figura 76 ilustra esta

idea:

Figura 6. que acepta

Mw Si

No

No

1MSi

No

M

2

Fuente: Autor

Construcción de la tiene dos cintas. Dada una entrada en la cinta 1, hace:

1. Copia en la cinta 2.

2. Simula a partir de en la cinta 2. Si se detiene en su estado , entonces se detiene en su estado

.

3. Borra el contenido de la cinta 2.

4. Copia en la cinta 2.

80

5. Simula a partir de en la cinta 2. Si se detiene en su estado (respectivamente ), entonces se

detiene en su estado (respectivamente ).

Queda probar que se detiene siempre, y que . Notar que a diferencia de las simulaciones

presentadas en la clase anterior, ahora de lo que se trata es de ejecutar directamente una por parte de otra

“invoca a la subrutina” , o en otras palabras, la función de transición de incluye un fragmento

que no es sino la función de transición de . En la clase siguiente, en que se trata la máquina de Turing universal,

este concepto se formaliza.

Otra propiedad de la clase que se demuestra a continuación es que es cerrada con respecto a la concatenación de

lenguajes, es decir que si entonces también ⦁ , siendo ⦁

Sean una que acepta y se detiene siempre, y una que acepta y se detiene siempre. Se va a

construir una que acepta ⦁ y se detiene siempre, con las siguientes características. Dada una entrada ,

con simula a partir de los primeros 0 símbolos de , y a partir de los últimos símbolos de ,

y si en ambos casos hay aceptación, entonces acepta . En caso contrario, hace lo mismo pero ahora con el

primer símbolo de y los últimos – símbolos de . Mientras no se detenga por aceptación, repite el

proceso con 2 y – símbolos de – símbolos, y así siguiendo hasta llegar a los y 0 símbolos, en cuyo

caso rechaza .

Construcción de la . tiene cinco cintas. A partir de una entrada en su cinta 1, tal que , hace:

1. Escribe el número 0 en la cinta 2. Sea i dicho número.

2. Escribe el número n en la cinta 3. Sea dicho número.

3. Escribe los primeros símbolos de en la cinta 4.

4. Escribe los últimos símbolos de en la cinta 5.

5. Simula en la cinta 4 a partir del contenido de dicha cinta, y simula en la cinta 5 a partir del

contenido de dicha cinta. Si ambas simulaciones se detienen en , entonces se detiene en .

6. Si , se detiene en .

7. Hace en la cinta – en la cinta 3, borra los contenidos de las cintas 4 y 5, y vuelve al

paso 3.

Algunas propiedades de clausura de la clase . Considerando las operaciones de intersección, unión y

concatenación de lenguajes, se cumple que también la clase es cerrada con respecto a ellas. En cambio, a

81

diferencia de la clase no es cerrada con respecto al complemento, lo que se probará más adelante. Al

demostrar primero que es cerrada con respecto a la unión de lenguajes, es decir que si

entonces . La prueba de que es cerrada con respecto a la intersección queda como ejercicio.

Sean una que acepta y una que acepta (ahora sólo se puede asegurar que estas se detienen

en los casos de aceptación). Se va a construir una que acepta . No sirve que la simule primero

y luego , porque de esta manera no acepta las cadenas de a partir de las que no se detiene. El

mismo problema ocurre simulando primero y después . La solución es otra: se simulan “en paralelo” las

y , y se acepta si alguna de las dos acepta. La figura 77 siguiente ilustra esta idea:

Figura 7. Simulación “en paralelo” las y

wSi

1M

M2

Si

Si

M

Fuente: Autor

Construcción de la . Sea la siguiente con cuatro cintas. Dada una entrada en la cinta 1, hace:

1. Copia en las cintas 2 y 3.

2. Escribe el número 1 en la cinta 4. Dicho número se va a referenciar como i en lo que sigue.

3. Simula, a partir de a lo sumo i pasos de la en la cinta 2, y a lo sumo i pasos de la en la

cinta 3. Si o se detienen en , entonces se detiene en .

4. Borra el contenido de las cintas 2 y 3.

5. Copia en las cintas 2 y 3.

6. Suma 1 al número i de la cinta 4.

7. Vuelve al paso 3.

Notar que la se detiene en su estado o no se detiene. Podría modificarse la construcción, haciendo que se

detenga en cuando detecta que tanto como se detienen en sus estados . Otra mejora en cuanto al

tiempo de trabajo de es no simular cada vez las dos desde el principio. En el paso 3 se indica que se simulan

a lo sumo i pasos porque y pueden detenerse antes. La implementación de estas simulaciones en términos

de la función de transición de podría consistir, asumiendo una representación en base unaria del contador i, en

82

avanzar sobre él a la derecha un dígito por cada paso simulado de y . Queda como ejercicio probar que

Una construcción alternativa, valiéndonos de las no determinísticas descriptas en la clase anterior, es

la siguiente. Si y son dos determinísticas

que aceptan los lenguajes y , respectivamente, se puede construir una que acepta a partir de

y Sea un estado que no está en ni en . La es la tupla

tal que , considerando todos los de

Es decir, al comienzo la pasa no determinísticamente a la configuración inicial de la MTD o a la

configuración inicial de la MTD , y después se comporta determinísticamente como ellas.

Al igual que la clase , es cerrada con respecto a la concatenación de lenguajes, es decir que si RE y

RE, entonces también ⦁ RE, lo que se prueba a continuación. Como en el caso de la unión de lenguajes

recursivamente numerables visto recién, debe tenerse en cuenta que las consideradas pueden no detenerse en

caso de rechazo.

Tal como se hizo con los lenguajes recursivos, se va a construir una que reconozca ⦁ simulando y

(las que reconocen y , respectivamente), primero a partir de 0 y símbolos de la entrada , después

a partir de 1 y – símbolos, y así siguiendo hasta llegar a y 0 símbolos, aceptando eventualmente. La

diferencia con el caso de los lenguajes recursivos está en que ahora, teniendo en cuenta las posibles no

detenciones de y , debe simularlas “en paralelo”. La primero hace simulaciones de un paso de y

con todas las posibles particiones de la entrada posibilidades), luego hace simulaciones de a lo

sumo dos pasos, y así siguiendo hasta eventualmente aceptar (éste es el caso en que al cabo de a lo sumo un

determinado número de pasos, , acepta los primeros símbolos de y acepta los últimos – símbolos

de ).

Construcción de la . Sea la siguiente con seis cintas, que a partir de una entrada en su cinta 1, tal

que hace:

1. Escribe el número 1 en la cinta 2. Sea dicho número.

2. Escribe el número 0 en la cinta 3. Sea dicho número.

3. Escribe el número en la cinta 4. Sea dicho número.

4. Escribe los primeros símbolos de en la cinta 5.

5. Escribe los últimos símbolos de en la cinta 6.

83

6. Simula a lo sumo pasos de en la cinta 5 a partir del contenido de dicha cinta, y simula a lo sumo

pasos de en la cinta 6 a partir del contenido de dicha cinta. Si ambas simulaciones se detienen en ,

entonces se detiene en .

7. Si , hace en la cinta 2, borra los contenidos de las cintas 3, 4, 5 y

8. 6, y vuelve al paso 2.

9. Hace en la cinta 3, – en la cinta 4, borra los contenidos de las cintas 5 y 6, y vuelve al

paso 4.

Al justificar formalmente la estructura de la jerarquía de la computabilidad presentada.

Sea la clase de los lenguajes complemento, con respecto a , de los lenguajes recursivamente

numerables. Formalmente: .

Considerando la siguiente figura 78 muestra una versión más detallada de la jerarquía de la

computabilidad:

Figura 8. versión más detallada de la jerarquía de la computabilidad

R

RE

CO-RE

Fuente: Autor

De la figura 78 se desprende que un lenguaje es recursivo si y sólo si tanto como son recursivamente

numerables, lo que se prueba a continuación.

. Se prueba fácilmente que La inclusión se cumple. También

vale porque . También se cumple la inversa, es

decir,

Sean y dos que aceptan los lenguajes y , respectivamente. Se va a construir una que se

detiene siempre y acepta , de la siguiente manera.

1. simula “en paralelo” las y .

2. Si se detiene en , entonces se detiene en su estado .

84

3. Y si se detiene en , entonces se detiene en su estado .

La figura 79 ilustra esta idea:

Figura 9. y dos que aceptan los lenguajes y

wSi

1M

Si

Si

M

M c No

Fuente: Autor

Se cumple que se detiene siempre porque para toda entrada , vale que , y por lo tanto o

aceptan . Queda la construcción de y la prueba de que .

En la última figura 78 que ilustra la jerarquía de la computabilidad, se distinguen cuatro categorías de lenguajes.

Enumeradas de acuerdo a su dificultad creciente, son:

1.

2. –

3. –

4. –

En este contexto, dado un par cualquiera de lenguajes y , se cumple alternativamente que:

Tanto como pertenecen a .

pertenece a – , y pertenece a – .

Tanto como pertenecen a –

Por el teorema, si está en también lo está . Dos lenguajes recursivos, los lenguajes {

y es un palíndrome}.

El lenguaje en – , con lo que se probara que , o en otras palabras, que hay problemas computables

que no son decidibles. En este caso pertenece a – , de acuerdo también al teorema. Notar que con la

existencia de se prueba además que , de acuerdo al teorema, o en otras palabras, que hay problemas que

no son computables. Adelantándonos, el primer lenguaje de – que corresponde al problema de la detención

de las , o directamente el problema de la detención (también conocido como halting problem). Este problema

85

computable no decidible aparece en la ya referida publicación de A. Turing en la que presenta las máquinas que

llevan su nombre. (Ricardo Rosenfeld, 2013)

El problema de la validez en la lógica de primer orden (o cálculo de predicados), es decir el problema de

determinar si una fórmula de la lógica de primer orden es válida, o lo que es lo mismo, si es un teorema (el trabajo

mencionado de Turing se relaciona con este problema).

El problema de correspondencia de Post, definido de la siguiente manera: dada una secuencia de pares de cadenas

de unos y ceros no vacías determinar si existe una secuencia de índices con tal

que las cadenas sean iguales.

El problema de determinar si una ecuación diofántica (ecuación algebraica con coeficientes y soluciones enteras)

tiene solución. El problema de teselación del plano: dado un conjunto finito de formas poligonales, determinar si

con ellas se puede cubrir el plano.

El problema de las palabras para semigrupos: dadas dos cadenas y un conjunto finito de igualdades entre

cadenas del tipo determinar si de la cadena se puede llegar a la cadena por medio de

sustituciones de subcadenas empleando las igualdades definidas.

Nos queda tratar el caso en que tanto como pertenecen a – lo que prueba que

. Un lenguaje de estas características, un tanto artificial. Luego los lenguajes más naturales de este tipo. A

modo de ilustración, un caso clásico de lenguaje no recursivamente numerable tal que su complemento tampoco

lo es, es el de los enunciados verdaderos de la teoría de números (o aritmética), de acuerdo al Teorema de

Incompletitud de Gödel3, que se referirá más adelante.

Las diferencias en el grado de dificultad de los lenguajes de las cuatro categorías señaladas se perciben a veces

mejor cuando se trata con restringidas, es decir con con restricciones en sus movimientos, sus cintas, etc.

Esto se analizará con cierto detalle en la Clase 5. Dado un conjunto de problemas indecidibles en el

marco de las generales, cuando se consideran con restringidas determinados problemas se mantienen

indecidibles mientras que otros pasan a ser decidibles. En el caso de estos últimos problemas, además, se pueden

destacar entre ellos diferencias en el costo de resolución (tiempo de ejecución de las ).

9.1 Problemas que las computadoras no pueden resolver : indecibilidad

3El teorema de incompletitud afirma que, bajo ciertas condiciones, ninguna teoría matemática formal capaz de describir los números naturales y la aritmética

con suficiente expresividad, es a la vez consistente y completa. Es decir, si los axiomas de dicha teoría no se contradicen entre sí, entonces existen

enunciados que no pueden probarse ni refutarse a partir de ellos. En particular, la conclusión del teorema se aplica siempre que la teoría aritmética en

cuestión sea recursiva, esto es, una teoría en la que el proceso de deducción pueda llevarse a cabo mediante un algoritmo.

86

El contenido de esta investigación se centra en los problemas indecidibles, es decir en los problemas de decisión

asociados a los lenguajes no recursivos, los lenguajes de – . Centrarse en los problemas decidibles, cuando se

analiza su complejidad computacional temporal.

Inicialmente se presenta el primer lenguaje recursivamente numerable que no es recursivo, que completa la

formalización de la jerarquía de la computabilidad definida en la clase anterior. Para ello se vale de la técnica de

diagonalización. Se muestra luego distintos casos de aplicación de esta técnica, y a partir de algunos de ellos se

obtiene otros lenguajes no recursivos. (John, 2008)

En el siguiente apartado hay representantes del conjunto – pero con otra técnica, la reducción de problemas.

Habiendo logrado probar la existencia de algunos primeros lenguajes de esta naturaleza con cierto esfuerzo

usando diagonalización, luego la obtención a partir de los mismos de nuevos representantes será más sencilla

empleando reducciones de problemas.

Para los desarrollos de esta clase se introduce antes que nada el concepto de máquina de Turing universal, el cual

se utilizara en las diagonalizaciones y reducciones. Hasta ahora se ha trabajado con que tratan, cada una, un

problema particular. Pero como modelo adecuado de una computadora la máquina de Turing puede ser también

“programable”, capaz de ejecutar cualquier a partir de cualquier entrada . En este caso, identificando con

a la universal, cumple que: Sus entradas son pares de la forma , siendo la codificación

de una , y una entrada, también codificada, de .

Dada la entrada , su ejecución consiste en simular a partir de .

La universal es como toda una tupla con sus propios estados y símbolos, y una

función de transición que establece cómo simular la cuyo código forma parte de su entrada. Una posible

manera de codificar una es la siguiente (para simplificar se consideran con una sola cinta; la codificación

se puede generalizar fácilmente a varias cintas). Dada

Los estados del conjunto se representan por los números , en notación binaria. Además,

y se representan en binario por los números , respectivamente.

Los símbolos del alfabeto se representan por los números , en notación binaria.

Los movimientos y se representan, respectivamente, por los números 1, 2 y 3, en notación binaria.

Finalmente, la función de transición se representa por una secuencia de 5- tuplas. Las tuplas se separan por el

símbolo numeral, es decir #, y sus componentes por medio de una coma.

87

Con estas consideraciones, la codificación de una consiste en la cadena formada por , en notación

binaria, seguida por el separador # y luego por la representación de la función de transición . Se antepone para

que se puedan identificar los estados y .

Si y la función de transición se define con

entonces el código de la es

La cadena en en realidad debe entenderse como la representación de , con sus símbolos

representados en notación binaria y separados entre sí por una coma. Para separar de se utilizan dos

numerales consecutivos.

Codificar las permite que las mismas se puedan enumerar, utilizando el orden canónico. La siguiente

computa, dado un número natural , el código de la -ésima según el orden canónico:

1. Hace

2. Crea la siguiente cadena w según el orden canónico.

3. Verifica si es un código válido de . Si no, vuelve al paso 2.

4. Si , escribe en la cinta de salida y se detiene en

5. Hace

6. Vuelve al paso 2.

En el paso 2 se generan cadenas en orden canónico con los símbolos que pueden formar parte del código de una

a partir de un ordenamiento establecido entre los símbolos.

En el paso 3 se verifica que las cadenas generadas tengan la forma , que los componentes y

respeten la codificación establecida, que ningún código de estado en supere el valor , etc.

Cuando en el paso 4 se cumple la igualdad , significa que se obtuvo el código .

Notar que en la enumeración canónica obtenida de las puede darse, para índices distintos

que Con estos elementos preparatorios ya se está en condiciones de probar la existencia de

primer lenguaje de –

El problema de la detención es computable no decidible. El problema de la detención (de las ), también

conocido como (por halting problem), es un problema clásico de la literatura, que se enuncia de la siguiente

manera: dada una y una cadena , ¿ se detiene a partir de ?. El lenguaje que lo representa es

se detiene a partir de

Al probar a continuación que – primero que , y luego que

88

Prueba de que . Sea la siguiente , que a partir de una entrada hace:

Si no es un código válido , rechaza. Simula a partir de . Si se detiene, acepta. La figura 80

ilustra el comportamiento de

Figura 10. El problema de la detención (de las ), también conocido como

M

HP

Si

No

M

Si

Fuente: Autor

Se cumple que acepta y se detiene a partir de

Prueba de que .

Al suponer que la siguiente tabla infinita de unos y ceros describe el comportamiento de todas las

con respecto a todas las cadenas de en lo que hace a la detención, considerando el orden canónico. El

valor de es 1 o 0, según la se detiene o no se detiene a partir de la cadena respectivamente.

Sea el lenguaje D = { | se detiene a partir de . Es decir, los elementos de son las cadenas tales que

. Probar que si entonces , y que , por lo que se cumplirá que .

Prueba de que Si el lenguaje fuera recursivo, también lo sería el lenguaje , dado que es

un caso particular de , que en lugar de considerar todos los pares sólo considera los pares

. Más precisamente, si entonces existe una que se detiene siempre y reconoce . Para

probar que , se va a construir una que se detiene siempre y reconoce .

A partir de una entrada trabaja de la siguiente manera: Encuentra el índice tal que según el orden

canónico. Genera . Simula a partir de y acepta (respectivamente rechaza) si acepta

(respectivamente rechaza).

En el paso genera canónicamente todas las cadenas hasta que encuentra la -ésima. Como se

detiene siempre, entonces se detiene siempre. Además se cumple se detiene a

partir de acepta acepta

Prueba de que

89

Al suponer que . Sea una que se detiene siempre y reconoce el lenguaje . A partir de se

construye la siguiente . Dada una entrada hace: Simula a partir de Si acepta, entra en

un loop. Y si rechaza, acepta (en realidad da lo mismo si rechaza). La figura 81 ilustra el comportamiento

de la

Figura 11. Comportamiento de la

wSi

No Si/No

M c

DM

Fuente: Autor

La descripción del fragmento de la función de transición de correspondiente al loop no tiene mayores

complicaciones: se puede reemplazar por un estado nuevo y definir una 5-tupla por cada símbolo

del alfabeto. En el paso 2 da lo mismo que acepte o rechace, si rechaza; lo importante es que se detenga.

La idea es que “le lleve la contra” a , en lo que respecta al comportamiento de la a partir de la

entrada si establece que se detiene a partir de (es decir si acepta), entonces no se detiene a

partir de y si establece que no se detiene a partir de (es decir si rechaza), entonces se detiene a

partir de Como la diagonal de la tabla representa el comportamiento de las respecto de las cadenas ,

entonces “el complemento a dos” de la diagonal (se permutan unos por ceros y ceros por unos), que difiere de

todas las filas de , representa el comportamiento de respecto de las cadenas . Esto entonces va a implicar

que no es ninguna de las , lo que se formaliza a continuación. Dado que la tabla incluye a todas las

tiene que ser alguna de ellas, denominada

Tabla 8. Comportamiento de las respecto de las cadenas

… … …

1 0 1 … 1 … 1 0 …

1 0 0 … 0 … 0 0 …

0 0 1 … 1 … 0 0 …

… … … … … … … … … … … … … … … … … … … …

1 1 0 … 0 … 1 1 …

… … … … … … … … … … 0 0 0 … 0 … 1 0 …

0 0 1 … 0 … 1 1 …

… … … … … … … … … …

90

Qué sucede al considerar la y la entrada

a. Si acepta wm, entonces por cómo se construyó se cumple que no se detiene a partir de . Pero

, así que vale que no se detiene a partir de . Por lo tanto, se cumple que rechaza

, lo que contradice la hipótesis.

b. Si en cambio rechaza , entonces por cómo se construyó se cumple que se detiene a partir de

. Pero como entonces se detiene a partir de . Dada la aclaración de queda que

acepta , lo que otra vez contradice la hipótesis.

De esta manera no puede existir la O dicho en otras palabras, es distinta de todas las enumeradas

en , lo que es absurdo porque en están todas las Y como la se construyó a partir de la

entonces tampoco puede existir Esto significa que .

La técnica empleada en el teorema anterior se denomina diagonalización. Es muy útil para probar que dos

conjuntos difieren en al menos un elemento, al que se lo suele denominar separador. En el caso anterior, el

separador que se encuentra entre las clases y es el lenguaje (en realidad también el lenguaje ). La idea

de la diagonalización es muy sencilla. En una de sus variantes, se toma como base una tabla de unos y ceros

y se utiliza el hecho de que “el complemento a dos” de su diagonal difiere de todas las filas: difiere de la primera

fila en el primer elemento, de la segunda fila en el segundo elemento, y así sucesivamente.

Otro lenguaje que no es recursivamente numerable. Se puede probar por diagonalización que de una

manera muy similar a cómo se probó que . En la siguiente tabla infinita de unos y ceros,

o 0 según la acepta o rechaza la cadena respectivamente.

De esta manera, acepta . Si y E

acepta , se cumple que

porque

porque

porque y así sucesivamente.

Es decir, no es ninguno de los lenguajes y como los lenguajes son todos los lenguajes recursivamente

numerables dado que en la tabla están todas las , entonces se cumple que . En términos de la tabla

, “el complemento a dos” de su diagonal, que representa el lenguaje , difiere de todas las filas de que

representan todos los lenguajes recursivamente numerables.

91

Notar que con lo desarrollado hasta este momento se cuenta con distintos caminos para formalizar los límites de la

computabilidad, es decir para probar la inclusión estricta . , porque de lo contrario sería

recursivo. Otro camino es recurrir directamente al lenguaje artificial que se presenta en la clase anterior, que

no pertenece a (ni siquiera pertenece a .

Una tercera alternativa es la diagonalización empleada en el caso anterior, con la que se encontró el lenguaje

separador entre y . Hay aún otra manera de probar que no todos los lenguajes son recursivamente

numerables, basada en la cardinalidad de los conjuntos infinitos: no puede haber más , y así lenguajes

recursivamente numerables, que ; la cantidad de lenguajes de es y como entonces

El caso aporta también un camino alternativo al del teorema del problema de la detención para probar que

. Claramente, el lenguaje acepta es recursivamente numerable, y como se vio que no es

recursivamente numerable, entonces se cumple que no es recursivo.

Otro lenguaje clásico de – es acepta . Claramente, el lenguaje es

recursivamente numerable, y no es recursivo porque de lo contrario el lenguaje sería recursivo (la prueba queda

como ejercicio). representa el problema de la pertenencia de una cadena a un lenguaje, o directamente el

problema de la pertenencia. Se lo conoce como lenguaje universal. En la clase siguiente se utilizara muy a

menudo para aplicar la técnica de reducción de problemas.

Al concluir con una apreciación sobre el significado de la indecidibilidad del problema de la detención,

generalizándola a todos los problemas indecidibles. Se ha demostrado la insolubilidad algorítmica del problema

general de la detención, es decir, se ha probado que no existe ninguna que lo resuelve sistemáticamente,

considerando las infinitas instancias . De todos modos ciertamente existe un algoritmo que resuelve

el problema cuando se considera una instancia particular uno que acepta o uno que rechaza. Para la

elección del algoritmo adecuado en cada caso habrá que apelar al ingenio, sin una técnica estándar en principio.

En otras palabras, un problema con una sola instancia siempre es decidible (obviamente nuestro interés radica en

los problemas con infinitas instancias).

Otro caso que ilustra esta dualidad de lo general y lo particular es el problema, ya mencionado, relacionado con

las ecuaciones diofánticas: dada una ecuación algebraica con distintas variables y coeficientes enteros, ¿existe una

solución con números enteros?

Dada la ecuación ¿existen valores enteros de que la resuelven? Se prueba que este

problema es indecidible. Por otro lado, ecuaciones diofánticas particulares son las que consideró P. de Fermat

cuando planteó su famoso teorema, conocido como último Teorema de Fermat, en el siglo XVII: dado , la

ecuación , siendo e mayores que , no tiene solución entera (Fermat no mostró la prueba del

92

teorema justificándose por lo pequeño del margen del libro en que lo publicó; el teorema se demostró recién en

1995). El problema de Fermat tiene una sola instancia, y como tal es decidible.

Un último caso de este tipo es el de la Conjetura de Goldbach, que establece que todo número natural par mayor

que 2 puede expresarse como la suma de dos números primos. Por tener una sola instancia, este problema es

decidible (al día de hoy sigue sin demostrarse). Naturalmente, y al igual que el problema de Fermat, la conjetura

de Goldbach se probaría fácilmente si el problema de la detención fuese decidible.

9.2 Reducción de problemas

Se completa el análisis de los problemas indecidibles, ahora con foco en la técnica de reducción de problemas,

que nos permitirá encontrar lenguajes no recursivos y no recursivamente numerables de una manera en general

mucho más sencilla que por medio de la diagonalización. Al considerar en su gran mayoría problemas

relacionados con . Al final, a partir de un teorema probado con una reducción de problemas, se presenta una

técnica que facilita aún más la demostración de la no recursividad, para un determinado tipo de lenguajes. La

noción de reducción de problemas es muy simple: para resolver un problema se lo relaciona con otro, que se sabe

cómo resolverlo; a partir de este conocimiento se resuelve el problema original.

Sean y dos lenguajes incluidos en . Existe una reducción del lenguaje al lenguaje , si y sólo si existe

una función total computable tal que La función se denomina

función de reducción. Que sea total computable significa, como se indicó previamente, que existe una que a

partir de cualquier cadena w computa en su cinta de salida y se detiene. En general, se identifica con a la

que computa . La figura 82 ilustra de reducción de problemas. Que haya una reducción de a significa,

entonces, que existe una que transforma toda cadena de en una cadena de , y toda cadena no

perteneciente a en una cadena no perteneciente a .

Figura 12. función se denomina función de reducción

*

1L

1w

2w

*

1L

1w

2w

f

f ( )

f ( )

Fuente: Autor

93

Se utiliza la notación para expresar que existe una reducción del lenguaje (o problema) al lenguaje (o

problema) .

El siguiente trabajo de investigación se aplica la reducción del problemas ya que se relaciona con un problema

clásico de la lógica, ya referido, y parte de un problema sobre cadenas de símbolos, también mencionado

previamente, que es el problema de correspondencia de Post (también conocido como ): dada una secuencia de

pares de cadenas de unos y ceros no vacías ¿existe una secuencia de índices con

, tal que las cadenas … y … sean iguales? Para los pares (1, 111), (10111, 10), (10, 0), se cumple que

(2, 1, 1, 3) es solución: en ambos casos se obtiene la cadena 101111110. En cambio, para los pares (10, 101),

(011, 11), (101, 011), se puede comprobar que no existe solución. Las soluciones pueden repetir índices; esto

significa que el espacio de búsqueda con el que se trata es infinito, lo que es un indicio de la indecidibilidad del

problema. Efectivamente, se prueba que existe una reducción de a PCP, por lo que PCP es indecidible. No se

construye esta reducción, sino que se utilizara PCP en otra reducción para probar, a continuación, que el problema

de la validez en la lógica de primer orden (también conocido como VAL) es indecidible.

Reducción de PCP a VAL. Sea es una fórmula válida de la lógica de primer orden}. Al construir

una reducción de a . Como no es recursivo, entonces se demuestra que tampoco lo es.

Dada una secuencia de pares de cadenas de unos y ceros no vacías , la función de reducción le

asignará a una fórmula de la lógica de primer orden válida si y sólo si tiene solución, en el sentido del

problema de correspondencia de Post.

Como símbolos de función se utiliza , de aridad 0 (es una constante), y y , de aridad 1. La idea es que

represente la cadena vacía, y y la concatenación, al final de una cadena, del dígito 0 o 1, respectivamente. De

este modo, la cadena de dígitos binarios se puede representar por el término , que para

facilitar la notación lo abreviaremos con (e).

Y como símbolo de predicado se utiliza , de aridad 2; el significado entendido para es que existe una

secuencia de índices , tal que el término s representa una cadena con subcadenas si de unos y ceros de la

forma , y el término representa una cadena con subcadenas de unos y ceros de la forma .

Definición de la función de reducción. La fórmula que se asigna, por la función de reducción a una secuencia

(sintácticamente correcta) de pares , es

con:

=

94

La función es total computable. Claramente, existe una que dada una secuencia sintácticamente

correcta genera la fórmula descripta previamente (en otro caso genera la cadena 1).

Se cumple . Se supone primero que es válida, lo que se denota con . Al probar

que tiene solución. Más específicamente, al encontrar un modelo para que establezca la existencia de una

secuencia de índices que soluciona .

El dominio de contiene todas las cadenas finitas de unos y ceros, incluyendo la cadena vacía . La

interpretación de e es , lo que se denota con . La interpretación de es la concatenación de un 0 al final

de una cadena, lo que se denota con . De la misma manera se define

Finalmente, la interpretación de es la siguiente: se cumple cuando existe una secuencia de índices

tal que y y son cadenas e unos y ceros de .

Como vale se cumple en particular . Claramente vale , porque se cumple para

. También vale , que establece que cuando el par está en , también lo está el par

, para Si , entonces existe una secuencia de índices , tal que y

. Definiendo una nueva secuencia de índices , vale si y = ti, por lo

que se cumple De esta manera, como se cumple por hipótesis y se ha demostrado

recién vale . Finalmente, y existe una solución para

Al suponer ahora que tiene solución, la secuencia de índices . Al probar que cualquiera sea el modelo ,

con una constante , dos funciones unarias y

, y un predicado binario , entonces satisface , es

decir . Dada la fórmula , se va a asumir y demostrar .

Para la interpretación de las cadenas finitas de unos y ceros en el dominio de se define inductivamente una

función denominada interpret, de la siguiente manera: interpret( ) = , interpret( ) = (interpret( )),

interpret( ) = (interpret(s)).

Por ejemplo, a la cadena 110 se le asigna

Más genéricamente, si una cadena s de dígitos

binarios tiene la forma , entonces interpret( ) =

( abreviado con

cómo se indico antes. Entonces, como vale , se cumple (interpret( ), (interpret( , para

. Como también vale , entonces para todo par se cumple (interpret( ), interpret( ))

95

, para . De esta manera, comenzando con si se considera repetidamente la última

observación se obtiene (interpret( ), interpret( , y dado que las cadenas y son

iguales porque es una solución de , entonces interpret( ) = interpret( ). De este modo se

cumple la fórmula y así .

Como una fórmula es insatisfactible si y sólo si su negación es válida, del caso anterior se desprende que el

lenguaje de las fórmulas satisfactibles de la lógica de primer orden también es indecidible (la prueba queda como

ejercicio). Lo mismo sucede con el lenguaje de los teoremas, porque por la sensatez y completitud de la lógica de

primer orden dicho lenguaje coincide con el de las fórmulas válidas. Por otra parte, el lenguaje de los teoremas (y

de las fórmulas válidas) es recursivamente numerable: a partir de axiomas y reglas de inferencia se puede

construir fácilmente una que lo reconoce (la prueba queda como ejercicio).

La indecidibilidad en la lógica de primer orden contrasta con la decidibilidad en la lógica proposicional, en la que

la satisfactibilidad y validez de las fórmulas se determinan mediante las tablas de verdad.

Por su parte, mientras el lenguaje de los teoremas de la teoría de números es recursivamente numerable, el de las

fórmulas verdaderas no lo es: por el Teorema de Incompletitud de Gödel, toda teoría recursiva y consistente que

contenga “suficiente” aritmética es incompleta. En particular, la indecidibilidad en la teoría de números se puede

probar mediante una reducción a partir del problema de pertenencia de la cadena vacía en un lenguaje

recursivamente numerable, que se demuestra es indecidible. La idea de la reducción es la siguiente. El lenguaje de

la teoría de números, si cuenta con las operaciones de suma y multiplicación (“suficiente” aritmética o

expresividad), como es el caso de la aritmética de Peano, permite expresar las configuraciones y computaciones

de las mediante números. Si una acepta , lo hace con una computación en la que ninguna

configuración mide, naturalmente, más que un número determinado . La reducción asigna entonces a cada

código una fórmula , que es verdadera si y sólo si representa una computación de que

acepta con configuraciones que no miden más que

Máquinas de turing restringidas. Los lenguajes regulares, libres de contexto y sensibles al contexto, se pueden

reconocer por restringidas en lo que hace a su poder computacional comparado con el de las sin

restricciones. Se analiza a continuación con cierto detalle.

Un autómata finito (abreviado con ) es una que tiene una sola cinta, la cinta de entrada, que es de sólo

lectura, y sobre la cual el cabezal se mueve solamente a la derecha desde el primer símbolo de la entrada. Cuando

el cabezal lee un blanco se detiene (acepta si y sólo si se detiene en un estado final). De este modo, los no

tienen memoria, salvo la que pueden proveer los estados. No existe un alfabeto dado que la única cinta es de

sólo lectura. Por lo tanto, la función de transición está compuesta por ternas del conjunto .

96

El autómata finito constituye un tipo de algoritmo ampliamente utilizado. Dos aplicaciones clásicas se relacionan

con la implementación del analizador lexicográfico de los compiladores, y la verificación automática de

programas utilizando modelos de transición de estados y lógica temporal (lo que se conoce como model

checking). Dado un , existe una gramática regular tal que Y dada una gramática regular ,

existe un tal que En otras palabras, el poder computacional de los alcanza para reconocer

todos los lenguajes regulares y sólo ellos.

97

ANEXO 10. Ordenamiento y búsqueda

Aunque el lenguaje común en ocasiones es adecuado para especificar un algoritmo, la mayoría de los matemáticos

y los especialistas en ciencias de la computación prefieren el seudocódigo por su precisión, estructura y

universalidad. El seudocódigo recibe este nombre porque se parece a un código real en lenguaje de computadora,

como C++ y Java. A diferencia de los lenguajes para computadora que deben preocuparse por puntos y comas,

mayúsculas y minúsculas, palabras reservadas y otros elementos, cualquier versión de seudocódigo es aceptable

siempre y cuando sus instrucciones no sean ambiguas. Nuestro seudocódigo se describe con operaciones y

funciones booleanas que representan identifica el lenguaje de la computadora con el cual el algoritmo funcionara

y se ejecuta directamente sobre la máquina de Turing.

Los algoritmos consisten en un título, una breve descripción del algoritmo, la entrada y la salida del algoritmo, y

las funciones que contienen las instrucciones del algoritmo. El algoritmo consta de una sola función. Para hacer

más conveniente la referencia a las líneas individuales dentro de una función, en ocasiones se numeran algunas de

ellas. La función del algoritmo en menor número de líneas numeradas.

Los algoritmos tienen las siguientes características:

a. Entrada. El algoritmo recibe datos de entrada.

b. Salida. El algoritmo produce una salida.

c. Precisión. Los pasos se establecen con precisión.

d. Determinismo. Los resultados intermedios de cada paso de ejecución son únicos y están determinados

sólo por las entradas y los resultados de los pasos anteriores.

e. Carácter finito. El algoritmo termina; es decir, se detiene después de ejecutar un número finito de

instrucciones.

f. Corrección La salida producida por el algoritmo es correcta; es decir, el algoritmo resuelve el

problema sin errores.

g. Generalidad El algoritmo se aplica a un conjunto de entradas.

Un programa de computadora, aun cuando se derive de un algoritmo correcto, puede ser inútil para cierto tipo de

entrada ya sea porque el tiempo necesario para correrlo o el espacio requerido para almacenar los datos, las

variables del programa, etcétera, son demasiado grandes. El análisis de un algoritmo se refiere al proceso de

derivar estimaciones del tiempo y el espacio necesarios para ejecutarlo. El problema de estimar el tiempo

requerido para ejecutar el algoritmo dependerá del lenguaje con el cual se esté operando, y en este caso es código

es binario.

98

En particular en el diseño y verificación del algoritmo, la lógica satisfactibilidad y otras propiedades de una

fórmula proposicional a veces se decidió sobre la base de una representación de la fórmula como un diagrama de

decisión binario . La satisfactibilidad proposicional tiene varias generalizaciones,

incluyendo satisfactibilidad al problema de la fórmula booleana cuantificados para la lógica clásica de primer y

segundo orden ( y , respectivamente), a los problemas de la satisfacción de las limitaciones para la

programación de enteros y el problema de la satisfactibilidad máximo. Muchos otros problemas de la

decisión, como los problemas de planificación y programación de problemas, pueden ser codificados en .

Suponga que se tiene un conjunto de trabajos, algunos etiquetados con “1” y otros etiquetados con “0”, y se

quiere encontrar el número de subconjuntos de que contienen al menos un trabajo “1”. Se construye un

algoritmo que examina todos los subconjuntos de y cuenta los que contienen al menos un trabajo “1” y después

se implementa este algoritmo como una secuencia en la máquina de Turing. Como un conjunto que tiene

elementos tiene subconjuntos, el programa requerirá al menos unidades de tiempo para la ejecución. No

importa cuáles sean esas unidades de tiempo, crece con tanta rapidez cuando se incrementa que, excepto por

los valores pequeños de , sería impráctico correr el programa.

Se planteara un algoritmos para ordenar, es decir, acomodar en orden los elementos de un conjunto. El problema

de ordenar un conjunto de objetos fue uno de los primeros problemas que se analizaron intensamente en las

ciencias de la computación. Muchas de las aplicaciones más conocidas del paradigma de diseño de algoritmos

Divide y Vencerás son algoritmos de ordenamiento. Durante los años sesenta, cuando el procesamiento comercial

de datos se automatizó en gran escala, el programa de ordenamiento era el que se ejecutaba con mayor frecuencia

en muchas instalaciones de cómputo. Una compañía de software se mantuvo operando durante años gracias a que

tenía un programa de ordenamiento mejor. Con el hardware actual, los aspectos de desempeño del ordenamiento

han cambiado un poco. En los años sesenta, la transferencia de datos entre almacenamiento lento (cinta o disco) y

la memoria principal era un importante cuello de botella del desempeño. La memoria principal era del orden de

100,000 bytes y los archivos a procesar eran varios órdenes de magnitud mayores. La atención se concentraba en

los algoritmos para efectuar este tipo de ordenamiento. Hoy, las memorias principales 1,000 veces mayores (o sea,

de 100 megabytes) son cosa común, y las hay 10,000 veces mayores (de unos cuantos gigabytes), de modo que la

mayor parte de los archivos cabe en la memoria principal.

Hay varias razones de peso para aplicar los algoritmos de ordenamiento. La primera es que tienen utilidad práctica

para el ordenamiento de los trabajo en la planta de producción una vez se estén seleccionando aquellas que

satisfagan las expresiones lógicas en cada nivel. El trabajo con conjuntos grandes de datos en las computadoras

(en nuestro caso MT máquina de Turing) se facilita si los datos están ordenados. La segunda es que se han ideado

99

una buena cantidad de algoritmos para ordenar (más de los que se cubren aquí), y nos convencerá del hecho de

que es posible enfocar un problema dado desde muchos puntos de vista distintos. El tratamiento de los algoritmos

suministrara algunas ideas acerca de cómo se puede mejorar un algoritmo dado y cómo escoger entre varios

algoritmos. La tercera es que el ordenamiento es uno de los pocos problemas para los que es fácil deducir cotas

inferiores firmes del comportamiento en el peor caso y en el caso promedio. Las cotas son firmes en el sentido de

que existen algoritmos que efectúan aproximadamente la cantidad mínima de trabajo especificada. Por ello, se

tienen algoritmos de ordenamiento prácticamente óptimos.

Al describir la mayor parte de los algoritmos, se supone que el conjunto a ordenar está almacenado en forma de

arreglo, de modo que se pueda acceder en cualquier momento a un elemento en cualquier posición; esto se

denomina acceso aleatorio. Si el acceso al conjunto es exclusivamente secuencial, se emplea el término sucesión

para hacer hincapié en que la estructura podría ser una lista ligada o un archivo secuencial, no sólo un arreglo. Se

define un arreglo dentro del intervalo de índices , un intervalo o subintervalo de ese arreglo será una

sucesión continua de elementos que está entre dos índices dados, primero y último, tales que 0 primero y

ultimo . Si ultimo primero, se dice que el intervalo está vacío.

Al suponer que cada elemento del conjunto a ordenar contiene un identificador, llamado clave, que es un elemento

de algún conjunto linealmente ordenado y que es posible comparar dos claves para determinar cuál es mayor o

que son iguales. Siempre se ordenan las claves en orden no decreciente. Cada elemento del conjunto podría

contener otra información además de la clave.

Si las claves se reacomodan durante el proceso de ordenamiento, la información asociada también se reacomodará

de manera acorde, pero a veces sólo se hablara de las claves sin mencionar explícitamente el resto del elemento.

Todos los algoritmos que consideraremos pertenecen a la clase de algoritmos de ordenamiento que podrían

comparar claves (y copiarlas) pero no deben aplicar otras operaciones a las claves. Estos son “algoritmos que

ordenan comparando claves”, o “algoritmos basados en comparación”. La medida primordial del trabajo que se

usa para analizar algoritmos de esta clase es el número de comparaciones de claves. Se establecen cotas inferiores

para el número de comparaciones que efectúa este tipo de algoritmos. Se tratan algoritmos de ordenamiento que

pueden efectuar operaciones distintas de la comparación de claves, y para los cuales son apropiadas otras medidas

del trabajo.

Los algoritmos de esta metodología se denominan ordenamientos internos porque se supone que los datos están

en la memoria de acceso aleatorio de alta velocidad de la computadora. Surgen diferentes aspectos de desempeño

cuando se desea ordenar conjuntos de datos tan grandes que no caben en la memoria. Los algoritmos para ordenar

100

grandes conjuntos de datos almacenados en dispositivos de almacenamiento externos más lentos, con restricciones

sobre la forma de acceder a los datos, se denominan ordenamientos externos. (John, 2008)

Al analizar algoritmos de ordenamiento, se considera qué tanto espacio adicional emplean (además del que

ocupan las entradas). Si la cantidad de espacio extra es constante con respecto al tamaño de las entradas, se

expresa que el algoritmo opera en su lugar.

A fin de que los algoritmos sean lo más claros posible, se usa Elemento y Clave como identificadores de tipo,

pero se tratara a Clave como un tipo numérico en cuanto a que usaran los operadores relacionales “ etc. Si

aparece una expresión de comparación de claves, como “E[i].clave,x” ,y los tipos reales no son numéricos

(String, por ejemplo), la sintaxis de Java requerirá una invocación de método, como “menor(E[i].clave, )”.

Esto también es necesario en muchos otros lenguajes.

Detalle de Java: Empleando la interfaz Comparable de Java, es posible escribir un procedimiento capaz de

comparar una amplia variedad de tipos de claves. El nombre de tipo Clave se sustituiría por la palabra reservada

Comparable. Un arreglo con elementos de tipo Elemento se declara como Elemento[] nombreArreglo; en

Java.

10.1 Ordenamiento por inserción.

Ordenamiento por inserción es un buen algoritmo de ordenamiento para comenzar porque la idea en la que se basa

es natural y general, sus análisis de peor caso y comportamiento promedio son fáciles de efectuar. También se usa

como parte de un algoritmo de ordenamiento más rápido.

La estrategia. Se parte de la sucesión de elementos en orden arbitrario (Ordenamiento por inserción se puede

usar con claves de cualquier conjunto ordenado linealmente, pero en el caso de las ilustraciones de palitos se

puede pensar que las claves son las alturas de los palitos, que son los elementos). La sucesión está establecida

como el lenguaje que ingresa en la a través de la cinta.

El procesamiento de cada trabajo es una medida normal en función del tiempo de terminación en el programa, en

la que se busca que sea el mínimo. Supongo que se ha ordenado algún segmento inicial de la sucesión. La figura

90 muestra una instantánea de la sucesión una vez que se han ordenado los cinco elementos del extremo

izquierdo. El paso general consiste en incrementar la longitud del segmento ordenado insertando el siguiente

elemento en el lugar correcto.

101

Sea el siguiente elemento a insertar en el segmento ordenado, es decir, es al elemento de la extrema izquierda

del segmento que todavía no se examina. Primero “se hace a un lado” a (es decir, se copia en una variable

local), dejando una vacante en su antigua posición. Luego se compara repetidamente con el elemento que está

inmediatamente a la izquierda de la vacante y, mientras sea menor, se pasara ese elemento a la vacante, dejando

una vacante en el lugar donde estaba; es decir, la vacante se desplaza una posición hacia la izquierda. Este proceso

se detiene cuando se acaban los elementos a la izquierda de la vacante actual, o cuando el elemento que está a la

izquierda de la vacante actual es menor o igual que .

En ese momento, se inserta en la vacante, como se muestra en la figura 90. Para poner en marcha el algoritmo,

basta con observar que el primer elemento sólo se puede considerar como un segmento ordenado. Al formalizar

esto para tener un procedimiento, se supone que la sucesión es un arreglo; sin embargo, la idea funciona también

con listas y otras estructuras secuenciales.

Figura 13. Inserción de en el orden correcto

Elementos en desorden

Ordenados Sin examinar

Insercion de x en el orden correctox =

Fuente: Autor

int desplaVac(Elemento[] E, int vacante, Clave x)

Condición previa: vacante no es negativa.

Condiciones posteriores: Sea posX el valor devuelto al invocador. Entonces:

102

1. Los elementos de cuyos índices son menores que posX están en sus posiciones originales y sus claves

son menores o iguales que .

2. Los elementos de que están en las posiciones posX+1, . . . , vacante son mayores que y se

desplazaron una posición a la izquierda respecto a la posición que ocupaban cuando se invocó

desplaVac.

El algoritmo y su análisis. Ahora se presenta los pormenores del procedimiento para ordenar. La tarea de la

subrutina desplaVac( , vacante, ) es desplazar elementos hasta que la vacante esté en la posición correcta para

colocar entre los elementos ordenados. El procedimiento devuelve el índice de la vacante, digamos posX, al

invocador. Las condiciones previas y posteriores se plantean en la figura 90. En otras palabras, desplaVac efectúa

la transición de la figura 90. Ahora ordenInsercion sólo tiene que invocar repetidamente a desplaVac,

formando un segmento ordenado cada vez más largo en el extremo izquierdo, hasta que todos los elementos estén

en ese segmento.

El procedimiento desplaVac adopta la forma representativa de las rutinas de búsqueda generalizada. Si no hay

más datos que examinar, fracasar; si hay más datos, examinar uno, y si es el que se está buscando, tener éxito; en

caso contrario, continuar con los datos no examinados. Puesto que hay dos casos para terminar, no sería

conveniente usar un ciclo while, a menos que se usara un break con uno o más de los casos para terminar. La

formulación recursiva es sencilla.

int desplaVacRec(Elemento[] E, int vacante, Clave x)

int posX;

1. if (vacante 0)

2. posX vacante;

3. else if (E[vacante1].clave x)

4. posX vacante;

5. else

6. E[vacante] E[vacante1];

7. posX desplaVacRec(E, vacante1, x);

8. return posX;

Para verificar que se está usando recursión correctamente en la línea 7, se observa que la invocación recursiva

está operando con un intervalo más pequeño, y que su segundo argumento no es negativo, con lo que se satisface

la condición previa (¿Verificar la cadena de razonamiento que nos dice que vacante-1 no es negativa; ¿por qué

no puede ser negativa?) Ahora es sencillo demostrar la corrección al recordar que se puede suponer que la

invocación recursiva de la línea 7 logra su objetivo.

103

Aunque el procedimiento para desplaVacRec es muy sencillo, si al visualizar el rastreo de activación para el -

ésimo elemento de a insertar, se da cuenta que la profundidad de la recursión, o la pila de marcos, podría crecer

hasta un tamaño . Esto podría ser indeseable si es grande. Por tanto, éste es un caso en que conviene convertir

la recursión en una iteración, una vez que se haya constatado que todo funciona correctamente. (Tratar de optimar

un programa que no funciona ciertamente sería útil.) El objetivo no es tanto ahorrar tiempo como ahorrar espacio.

En realidad muchos compiladores, si se les pide optimar a desplaVacRec, efectuarán la transformación

automáticamente. El algoritmo completo que sigue incluye la versión de desplaVac codificada iterativamente.

Ordenamiento por inserción.

Entradas: , un arreglo de elementos, y , el número de elementos. El intervalo de los índices es

Salidas: , con los elementos en orden no decreciente según sus claves.

Comentario: Las especificaciones de la subrutina desplaVac se da a continuación:

void ordenInsercion(Elemento[] E, int n)

int indicex;

for (indicex 1; indicex n; indicex )

Elemento actual E[indicex];

Clave x actual.clave;

int posX desplaVac(E, indicex, x);

E[posX] actual;

return;

int desplaVac(Elemento[] E, int indicex, Clave x)

int vacante, posX;

vacante indicex;

posX 0; // Suponemos fracaso.

while (vacante 0)

if (E[vacante1].clave x)

posX vacante; // Éxito.

break;

E[vacante] E[vacante1];

vacante ––; // Seguir buscando.

return posX;

Complejidad de peor caso. Para el análisis, se usa en lugar de índicex. Para cada valor de , el número

máximo de comparaciones que pueden efectuarse (en una invocación de la rutina iterativa desplaVac o en una

invocación de nivel más alto de la rutina recursiva desplaVacRec) es Por tanto, el total es

104

Se ha establecido una cota superior para el comportamiento de peor caso; hay que pensar un momento para

verificar que en verdad existen entradas con las que se efectúan comparaciones. Uno de esos peores

casos es cuando las claves están en orden inverso (es decir, decreciente). Así,

Comportamiento promedio. Al suponer que todas las permutaciones de las claves son entradas igualmente

verosímiles. Primero se determina cuántas comparaciones de claves se efectúan en promedio para insertar un

elemento nuevo en el segmento ordenado, es decir, en una invocación de desplaVac con cualquier valor

específico de (que se usa en vez de índicex). Para simplificar el análisis, se supone que todas las claves son

distintas.

Hay posiciones en las que puede colocarse . La figura muestra cuántas comparaciones se efectúan

dependiendo de la posición. La probabilidad de que vaya en cualquier posición específica es . (Esto

depende del hecho de que el algoritmo todavía no ha examinado a . Si el algoritmo hubiera tomado antes alguna

decisión con base en el valor de , no se podría suponer por fuerza que es uniformemente aleatorio con respecto

a las primeras claves.) Así pues, el número medio de comparaciones que se efectúan en desplaVac para

encontrar la posición del -ésimo elemento es

Ahora se obtiene la sumatoria para las inserciones:

donde se sustituye para obtener la última sumatoria. Ya vimos, por la ecuación que , se

puede incorporar el 1 que está antes de la sumatoria para hacer que el límite inferior . Olvidándonos de los

términos de orden inferior, tenemos:

Es evidente que Ordenamiento por inserción es un ordenamiento en su lugar si se usa la versión iterativa de

desplaVac. Con la versión recursiva, la pila de marcos puede crecer hasta

105

Cotas inferiores para el comportamiento de ciertos algoritmos de ordenamiento. Al pensar que el elemento

cuya clave es el cual ocupa la posición “vacante” del arreglo, mientras Ordenamiento por inserción compara

con la clave que está a su izquierda. Entonces, después de cada comparación, Ordenamiento por inserción no

cambiará de lugar ningún elemento o simplemente intercambiará dos elementos adyacentes. Se demuestra que

todos los algoritmos de ordenamiento que efectúan semejante traslado “local” limitado de elementos, después de

cada comparación, deben efectuar aproximadamente la misma cantidad de trabajo que Ordenamiento por

inserción. (Pinedo, 1995)

Una permutación de elementos se puede describir con una función uno a uno del conjunto sobre

sí mismo. Existen permutaciones distintas de elementos. Sean los elementos de la sucesión no

ordenada . A fin de simplificar la notación en este análisis, supóngase que los elementos a ordenar están en las

posiciones de no en . Existe una permutación tal que, para 1 es la posición

correcta de una vez que la sucesión está ordenada. Sin perder generalidad, se puede suponer que las claves son

los enteros , ya que se puede usar 1 en lugar de la clave más pequeña, 2 en lugar de la clave más pequeña

de las restantes y así sucesivamente, sin tener que modificar las instrucciones ejecutadas por el algoritmo.

Entonces, la entrada sin ordenar es Al considerar la sucesión de entrada

implica que la primera clave, 2, debe ir en la segunda posición, lo cual es obvio. π (2) = 4 porque la segunda clave,

4, debe ir en la cuarta posición, y así sucesivamente. Identificar la permutación con la sucesión

Una inversión de la permutación es un par tal que y . Si es una inversión,

las claves -ésima y -ésima de la sucesión están en desorden una respecto a la otra. La permutación 2, 4, 1, 5, 3

tiene cuatro inversiones: (2, 1), (4, 1), (4, 3) y (5, 3). Si un algoritmo de ordenamiento elimina cuando más una

inversión después de cada comparación de claves (al intercambiar elementos adyacentes, como hace

ordenamiento por inserción), entonces el número de comparaciones efectuadas con la entrada

será por lo menos el número de inversiones de . Por ello, se investigaran las inversiones.

Es fácil demostrar que existe una permutación con inversiones. (¿Cuál permutación?) Por tanto, el

comportamiento de peor caso de cualquier algoritmo de ordenamiento que elimina cuando más una inversión en

cada comparación de claves deberá estar en .

Para obtener una cota inferior del número medio de comparaciones efectuadas por tales algoritmos de

ordenamiento, se calcula el número medio de inversiones que hay en las permutaciones. Cada permutación se

puede aparear con su permutación transpuesta

106

La transpuesta de 2, 4, 1, 5, 3 es 3, 5, 1, 4, 2. Cada permutación tiene una transpuesta única y es distinta de su

transpuesta (para ). Sean y enteros entre 1 y , y supóngase que . Entonces es una inversión en

una y sólo una de las permutaciones y transpuesta de . Existen pares de enteros semejantes. Por

tanto, cada par de permutaciones tiene permutaciones en conjunto, y por ende un promedio de

Así, en total, el número medio de inversiones que hay en una permutación es de se ha

demostrado el teorema siguiente. Ver anexo Teorema 15.

Puesto que ordenamiento por inserción efectúa comparaciones de claves en el peor caso y

aproximadamente en promedio, es prácticamente lo mejor que se pueden lograr con cualquier algoritmo que

opere “localmente”, intercambiando sólo elementos adyacentes. Desde luego, a estas alturas no es obvio que

alguna otra estrategia pueda funcionar mejor, pero si existen algoritmos significativamente más rápidos deberán

trasladar elementos más de una posición a la vez. (Sara Baase, 2002)

10.2 Divide y vencerás.

El principio en que se basa el paradigma de diseño de algoritmos divide y vencerás es que (a menudo) es más fácil

resolver varios casos pequeños de un problema que uno grande. Los algoritmos emplean el enfoque de Divide y

vencerás: dividen el problema en ejemplares más pequeños del mismo problema (en este caso, conjuntos más

pequeños a ordenar), luego resuelven (vencen) los ejemplares más pequeños de forma recursiva (o sea, empleando

el mismo método) y por último combinan las soluciones para obtener la solución correspondiente a la entrada

original. Para escapar de la recursión, al resolver directamente algunos casos pequeños del problema. En

contraste, Ordenamiento por inserción se limitó a “recortar” un elemento para crear un subproblema. (Cormen &

Leiserson, 2010)

Al ver un caso excelente de divide y vencerás: busqueda binaria. El problema principal se dividió en dos

subproblemas, uno de los cuales ni siquiera se tenía que resolver. En general, se puede describir divide y vencerás

con el esqueleto de procedimiento de la algoritmo descrito a en la figura 91.

Para diseñar un algoritmo de divide y vencerás específico, se debe especificar las subrutinas

resolverDirectamente, dividir y combinar. El número de casos más pequeños en los que se divide la entrada es

Con una entrada de tamaño sea el número de pasos efectuados por resolverDirectamente, sea el

número de pasos efectuados por dividir, y sea el número de pasos efectuados por combinar. Entonces, la

forma general de la ecuación de recurrencia que describe la cantidad de trabajo efectuada por el algoritmo es

107

para pequeño

Figura 14. El esqueleto de divide y vencerás

resolver(I)

n tamaño(I);

if (n pequeño)

solucion resolverDirectamente(I);

else

dividir en .

para cada

resolver( );

solucion combinar( , . . . , );

return solucion;

El esqueleto de divide y vencerás con los casos base para pequeño. En muchos algoritmos

divide y vencerás, el paso de dividir o bien el paso de combinar es muy sencillo, y la ecuación de recurrencia

para es más simple que la forma general. El teorema maestro da soluciones para una amplia gama de ecuaciones

de recurrencia de divide y vencerás.

Quicksort y Mergesort, los algoritmos de ordenamiento, difieren en la forma en que dividen el problema y luego

combinan las soluciones, o subconjuntos ordenados. Quicksort se caracteriza como “división difícil, combinación

fácil”, mientras que Mergesort se caracteriza como “división fácil, combinación difícil”. Fuera del procesamiento

que requieren las invocaciones de procedimientos, se vera que el “trabajo real” se efectúa en la sección “difícil”.

Ambos procedimientos de ordenamiento tienen subrutinas para realizar su sección “difícil”, y tales subrutinas son

útiles por derecho propio. En el caso de Quicksort, el “caballito de batalla” es partir, y es el paso dividir del

esqueleto general; el paso combinar no hace nada. En el caso de Mergesort, el “caballito de batalla” es fusionar, y

es el paso combinar; el paso dividir sólo efectúa un cálculo sencillo. Ambos algoritmos dividen el problema en

dos subproblemas. Sin embargo, en Mergesort los problemas son de tamaño comparable (más o menos un

elemento), mientras que en Quicksort no se garantiza una división pareja. Esta diferencia da pie a características

de desempeño muy distintas, que se descubrira durante el análisis de los respectivos algoritmos. (Sara Baase,

2002). En el nivel más alto, HeapSort no es un algoritmo divide y vencerás, pero usa operaciones de montón que

pertenecen a la categoría Divide y vencerás. La forma acelerada de Heapsort emplea un algoritmo Divide y

vencerás más avanzado. (John, 2008)

En las limitaciones de la investigación reaparecera en una forma un poco distinta para la computación en paralelo.

108

ANEXO 11. Sistemas Secuenciales Biestables

Biestable con reloj. El biestable básico, tal como esta, es un sistema secuencial asíncrono. Por la adición de

compuertas a las entradas del sistema básico, puede haberse que el biestable responda a niveles de entrada durante

la ocurrencia de un pulso de reloj. EL biestable RS con reloj que se muestra en la figura 51 consta de un biestable

básico NOR y dos compuertas . Las salidas de las dos compuertas permanecen en 0 en tanto que el pulso de

reloj (agreviado , de las iniciales en ingles de clock pulse) sea 0, sin importar los valores de entrada y .

Cuando el pulso de reloj va a 1, se permite que la información de las entradas alcancen al biestable básico.

El estado de ajuste se alcanza con . Para cambiara al estado despejado, las entradas deben

ser . Tanto con la ocurrencia de un pulso de reloj provoca que ambas salidas

momentáneamente a 0. Cuando se elimina el pulso, el estado del biestable es indeterminado, esto es, puede

resultar cualquier estado, dependiendo de si la entrada de ajuste o la de restaurar del sistema biestable básico

permanezca en 1 durante un tiempo más prolongado antes de la transmisión a 0 al fin del pulso.

El símbolo grafico para el biestable S con reloj se muestra en la figura 51. Tiene tres entradas: . La

entrada no está indicada dentro de la caja, debido a que se reconoce por el triangulo pequeño marcado. El

triangulo es un símbolo para un indicador dinámico y denota el hecho de que el biestable responde a una

transición de reloj en una señal bajo nivel (binario 0) a un alto nivel (binario 1).

La salida del biestable están marcadas con y dentro de la caja. Pueden asignarse al biestable una variable con

nombre diferente aunque este escrita dentro de la caja. En ese caso, la letra que se elige para la variable del

biestable se marca fuera de la caja junto a la línea de salida. El estado del biestable está determinado por el valor

de su salida normal . Si se desea obtener el complemento de la salida normal, no es necesario insertar un

inventor, ya que el valor complementado está disponible directamente mediante la salida .

Figura 15. (Árbol sintáctico) Biestable con pulso de reloj

&0

0

0

&0

0

0

R

S

Q

Q'

&0

0

0

0

&0

0

0

0

CP

Fuente: Autor

109

La tabla característica para el biestable se muestra en la figura. En esta tabla se resume la operación del biestable

en una forma tabular. es el estado binario del biestable en un momento dado (referido como estado presente),

las columnas y dan los valores posibles de las entradas es el estado del biestable después de la

ocurrencia de un pulso de reloj (referida como estado siguiente).

La ecuación característica del biestable se deriva en el mapa. Esta ecuación especifica el valor del estado siguiente

como una función del estado presente y las entradas. La ecuación característica es una expresión algebraica para

la información binaria de la tabla característica. Los dos estados indeterminados están marcados con en el mapa,

ya que pueden resultar en 1 o bien en 0. Sin embargo, la relación debe incluirse como parte de la ecuación

característica para especificar que tanto como no pueden ser iguales a 1 en forma simultánea.

Biestable . El biestable que se muestra en la figura 52 es una modificación del biestable con reloj. Las

compuertas 1 y 2 forman un biestable básico y las compuertas 3 y 4 modifican para formar un biestable con

reloj. La entrada va en forma directa a la entrada , y su complemento, a través de la compuerta 5, se aplica a la

entrada . En tanto que el pulso de reloj en la entrada este en 0, las compuertas 3 y 4 tienen un 1 en sus salidas,

sin importar el valor de las otras entradas. Esto se apega al requisito de que las dos entradas de un biestable básico

permanezcan inicialmente en el nivel 1. La salida se muestra durante la ocurrencia de un pulso de reloj. Si el

1, la salida de la compuerta 3 pasa a 0, cambiando el biestable al estado de ajuste (a menos que ya este puesto ), si

es 0, la salida de la compuerta 4 va a 0, cambiando el biestable al estado despejado.

El biestable recibe su denominación debido a su capacidad de transferir datos en el biestable. En forma básica

es un biestable con un inversor en la salida . El inversor agregado reduce el número de entradas de dos a una.

Este tipo de biestable algunas veces se denomina un seguro –D con compuertas. La entrada con frecuencia

recibe designación variable (de la inicial en ingles de compuertas, es decir gate) para indicar que esta entrada

habilita el seguro con compuertas para hacer posible la entrada de información dentro del biestable.

El símbolo para un biestable temporizado se muestra en la figura 52. La tabla característica se lista en la parte

y se deriva la ecuación características en la parte d. La ecuación característica muestra el estado siguiente del

biestable es el mismo de la entrada y es independiente del valor del estado presente.

Figura 16. (Árbol sintáctico) Biestable con pulso de reloj

110

&0

0

0

&0

0

0

D

Q

Q'

&0

0

0

&0

0

0

C

Fuente: Autor

Biestable . Un biestable es un refinamiento del biestable ya que el estado indeterminado del tipo se

define ene el tipo . Las entradas y se comportan como las entradas y para ajustar y despejar el biestable

(obsérvese que en un biestable , la letra es para ajustar y la letra es para el despeje). Cuando se aplican

señales de entrada en forma simultánea a como , el biestable cambia a su estado complementario, esto es, si

cambia a y viceversa.

Un biestable temporizado se muestra en la figura 53. La salida opera con las entradas y de modo que

el biestable se despeja durante un pulso de reloj solo si era previamente 1. En forma similar, la salida opera

con las entradas y de modo que el biestable se ajusta con un pulso de reloj solo si era previamente 1.

Como se muestra en la tabla característica en la figura el biestable se comporta como un biestable excepto

cuando tanto como son iguales a 1. Cuando y son 1, el pulso de reloj se transmite solo a través de una

compuerta (la que tenga conectada su entrada a la salida del biestable que al presente sea igual a 1).

Por tanto, si la salida de la compuerta superior llega a ser 1 bajo la aplicación de un pulso de reloj, y el

biestable se despeja. Si , la salida de la compuerta inferior llega a ser un 1 y el biestable se ajusta. En

cualquier caso, el estado de la salida del biestable se complementa.

Las entradas en el símbolo grafico para el biestable deben marcarse con una (bajo ) y (bajo ). La

ecuación característica se da en la figura y se deriva mediante el mapa de la tabla característica.

Obsérvese que debido a la conexión de retroalimentación en el biestable , una señal que permanece en 1 (en

tanto ) una vez que las salidas se han complementado provocara transiciones repetidas y continuas de las

salidas. Para evitar esta operación indeseable, los pulsos de reloj deben tener una dirección más corta que el

111

retardo de propagación a través del biestable. Este es un requisito de restricción, ya que la operación del sistema

depende del ancho de los pulsos. Por esta razón, los biestable nunca se construyen como se muestra en la

figura. La restricción en el ancho del pulso puede eliminarse con una construcción de maestro-esclavo o de

disparo en borde. El mismo razonamiento se aplica al biestable que se presenta a continuación.

Figura 17. (Árbol sintáctico) Biestable con pulso de reloj

>=10

0

0

>=10

0

0

KQ

Q'

&0

0

0 0

&0

0

0 0

C

K

0

0

Fuente: Autor

Biestable . El biestable es una versión de una sola entrada del biestable . Como se muestra en la figura 54,

el biestable se obtiene mediante un tipo si ambas entradas se ligan. La denominación proviene de la

capacidad del biestable para conmutar (de la inicial del término ingles: toggle), o cambiar de estado. Sin importar

el estado presente del biestable, asume el estado complementario cuando ocurre el pulso de reloj mientras la

entrada es lógica 1. El símbolo, la tabla característica y la ecuación característica del biestable se muestra en

la figura, respectivamente.

Figura 18. (Árbol sintáctico) Biestable con pulso de reloj

112

>=10

0

0

>=10

0

0

Q

Q'

&0

0

0 0

&0

0

0 0

0

0

Fuente: Autor

Los biestable que se introducen los tipos disponibles más comunes en el comercio. Los procedimientos de análisis

y diseño que se desarrollan en este apartado son aplicables para cualquier biestable temporizado una vez que se

define su tabla característica.

Disparo del biestable. El estado de un biestable se cambia por una modificación momentánea en la señal de

entrada. Este cambio momentáneo se denomina gatillo y la transición que provoca se dice que dispara al biestable.

Los biestable asincrónicos, como los sistemas lógicos básicos, requieren una entrada de gatillo definida por un

cambio de nivel de señal. Este nivel debe volver a su valor inicial (0 en el biestable NOR y 1 en el ) antes de que

aplique un segundo gatillo. Los biestables temporizados se disparan por pulsos. Un pulso comienza desde un valor

inicial de 0, pasa en forma momentánea a 1 y después de un corto tiempo, regresa a su valor inicial de 0, pasa en

forma momentánea a 1 y después de un corto tiempo, regresa a su valor 0 inicial. El intervalo de tiempo desde la

aplicación del pulso hasta que ocurre la transición de la salida es un factor crítico que requiere más investigación.

Como se observo en el diagrama de bloques en la figura 54, un sistema secuencial tiene una trayectoria de

retroalimentación entre el sistema combinacional y los elementos de memoria. Esta trayectoria puede producir

inestabilidad y las salidas de los elementos de memoria (biestables) se cambian, mientras las salidas del sistema

combinacional que van a las entradas de los biestables se muestran por el pulso de reloj. Este problema de

temporizado puede evitarse si las salidas de los biestables no inician el cambio sino hasta que el pulso de entrada

ha regresado a 0. Para asegurar tal operación, un biestable debe tener un retardo de propagación de señal desde la

entrada a la salida que exceda la duración del pulso. Este retardo por lo común es muy difícil de controlar so el

diseñador depende por completo del retardo de propagación de las compuertas lógicas. Una forma de asegurar el

retardo apropiado es incluir dentro del sistema biestable una unidad de retardo física que tenga un retardo igual o

113

mayor que la duración del pulso. Una manera adecuada de resolver el problema del temporizado de la

retroalimentación es hacer sensitivo al biestable a la transición del pulso más que a la duración del pulso.

Un pulso de reloj puede ser positivo o bien negativo. Una fuente positiva de reloj permanece en 0 durante el

intervalo entre pulsos y pasa a 1 al ocurrir un pulso. El pulso pasa a través de dos transiciones de señal: desde 0 a

1 y el regreso de 1 a 0. La transición positiva se define como el borde positivo y la transición negativa como el

borde negativo. Esta explicación también se aplica a los pulsos negativos.

Los biestable temporizados se disparan durante el borde positivo del pulso, y la transición de estado principia tan

pronto el pulso alcanza el nivel lógico 1. El nuevo estado del biestable puede aparecer en las terminales de salida

mientras el pulso de entrada todavía este en 1. Si las otras entradas del biestable cambian mientras el reloj todavía

este en 1, el biestable iniciara la respuesta a esos nuevos valores y puede ocurrir un nuevo estado de salida.

Cuando esto sucede, la salida de un biestable no puede aplicarse a las entradas de otro biestable cuando el mismo

pulso de reloj los dispara a ambos. Sin embargo, si puede hacerse que el biestable responda a la transición de

borde positiva (o negativa) solamente, en lugar de la duración completa del pulso, entonces puede eliminarse el

problema de transición múltiple.

Una forma de hacer que el biestable responda solo a una transición del pulso es utilizar un acoplamiento capacitor.

En esta configuración, un sistema (resistor-capacitor) se inserta en la salida de reloj del biestable. Este sistema

genera un pico como respuesta a un cambio momentáneo de la señal de entrada. Un borde positivo emerge de

dicho sistema con un pico positivo, y un borde negativo emerge con un pico negativo. El disparo por bordes se

logra diseñando el biestable de modo que desprecie un pico y dispare una ocurrencia de otro pico. Una forma para

lograr el disparo por borde es utilizar un biestable maestro-esclavo o disparando por borde como se expone a

continuación.

Biestable maestro-esclavo. Un biestable maestro-esclavo se construye mediante dos biestable separados. Un

sistema sirve como un maestro y el otro como un esclavo, y el sistema global se conoce como un biestable

maestro-esclavo. El diagrama lógico de un biestable maestro-esclavo se muestra en la figura 55. Consta de un

biestable maestro, un biestable esclavo y un inversor. Cuando el pulso de reloj es 0, la salida del inversor es 1.

Ya que la entrada de reloj del esclavo es 1, el biestable está habilitado si la salida es igual a , en tanto que es

igual a . El biestable maestro se habilita porque Cuando el pulso llega a 1, entonces la información en

las entradas externas y se transmite al biestable maestro. Sin embargo, el biestable esclavo está aislado

mientras el pulso este en su nivel 1, ya que la salida del inversor es 0. Cuando el pulso regresa a 0, el biestable

114

maestro está aislado, lo cual evita que lo afecten las entradas externas. El biestable esclavo pasa entonces al

mismo estado que el del biestable maestro.

Figura 19. (Árbol sintáctico) Relaciones de tiempos en un biestable maestro-esclavo

Q

QSET

CLR

S

R Q

QSET

CLR

S

R

Q

Q'

S

R

C

Y

Y'

Fuente: Autor

Las relaciones de temporizados ilustran la secuencia de eventos que ocurren en un biestable maestro esclavo. Se

supone que el biestable está en el estado despejado antes de la ocurrencia de un pulso, de modo que y

. Las condiciones de entrada son y el siguiente pulso de reloj cambiara el biestable al estado ajustar

con . Mediante la transición de un pulso de 0 a 1, el biestable maestro esta restaurado y cambia a 1. El

biestable esclavo no es aceptado porque su entrada es 0. Ya que el biestable maestro es un sistema interno, su

cambio de estado no es obvio en las salida y . Cuando el pulsor regresa a 0, se permite que la información del

maestro pase al esclavo, haciendo que la salida externa sea . Obsérvese que la entrada externa debe

cambiarse al mismo tiempo que el pulso pasa a través de su transición de borde negativo. Este se debe a que una

vez que la entrada alcanza 0, el maestro está habilitado y sus entradas y no tienen influencia hasta que

ocurre el siguiente pulso de reloj. Por esto en un biestable maestro-esclavo es posible cambiar la salida del

biestable y su información de entrada con el mismo pulso de reloj. Debe tomarse en cuenta que la entrada puede

llegar mediante la salida de otro biestable maestro-esclavo que se cambio con el mismo pulso de reloj.

El comportamiento del biestable maestro-esclavo que acaba de describirse dicta que los cambios de estado en

todos los biestables coincidan con la transición de borde negativo del pulso. No obstante, algunos biestables

maestro-esclavo cambian los estados de salida en la transición de borde positivo de los pulsos de reloj. Esto

sucede en biestables que tienen un inversor adicional entre la terminal y la entrada del maestro. Tales biestable

se disparan con pulsos negativos, de modo que el borde negativo del pulso afecte al maestro y el borde positivo

afecte al esclavo y las terminales de salida.

115

La combinación maestro-esclavo puede construirse para cualquier tipo de biestable por la adición de un biestable

temporizado con un reloj invertido para formar el esclavo. Un biestable maestro-esclavo construido con

compuertas se muestra en la figura 56. Consta de dos biestable; las compuertas 1 a 4 forman el biestable

maestro, y las compuertas 5 a la 8 forman el biestable esclavo. La información presente en las entradas y se

transmite al biestable maestro en el borde positivo de un pulso de reloj y se sostiene hasta que ocurre el borde

negativo del pulso de reloj, después del cual se permite que pase a través del biestable esclavo. La entrada de reloj

normalmente es 0, lo cual mantiene las salidas de las compuertas 1 y 2 en el nivel. Esto evita que las entradas y

afecten el biestable maestro. El biestable esclavo es un tipo temporizado, con el biestable suministrado las

entradas y con la entrada de reloj invertida por la compuerta 9. Cuando el reloj es 0, la salida de la compuerta 9 es

1, de modo que la salida es igual a y es igual a .

Cuando ocurre el borde positivo de un pulso de reloj, el biestable maestro se afecta y puede cambiar estados. El

biestable esclavo está aislado mientras que el reloj este en el nivel 1, ya que la salida de la compuerta 9

proporciona un 1 a ambas entradas de las compuertas 7 y 8 biestable básico. Cuando la entrada de reloj regresa

a 0, el biestable maestro está aislado mediante las entradas y y el biestable esclavo pasa al mismo estado del

biestable maestro. Se considera ahora un sistema digital que contiene muchos biestable maestro-exclavo, con las

salidas de algunos biestable que van a las entradas de otros biestable.

Se supone que las entradas de pulso de reloj a todos los biestables están sincronizadas (ocurren al mismo tiempo).

Al principio de cada pulso de reloj, algunos de los elementos maestros cambian estado, pero todas las salidas

biestable permanecen en sus valores previos. Después de que el pulso de reloj regresa a 0, algunas de las salidas

cambian de estado maestro hasta el siguiente pulso de reloj. Así que, los estados de biestables en el sistema

pueden cambiarse en forma simultánea durante el mismo pulso de reloj, aun cuando las salidas de los biestables

estén conectadas a entradas de biestable.

Figura 20. (Árbol sintáctico) Biestable maestro-esclavo con pulsos de reloj

116

&0

0

0

&0

0

0

Q

Q'

&0

0

0

&0

0

0

&0

0

0

&0

0

0

K

J

&0

0

0 0

&0

0

0 0

1C

Y

Y'

Fuente: Autor

Se supone que las entradas de pulso de reloj a todos los biestables están sincronizadas (ocurren al mismo tiempo).

Al principio de cada pulso de reloj, algunos de los elementos maestros cambian estado, pero todas las salidas

biestable permanecen en sus valores previos. Después de que el pulso de reloj regresa a 0, algunas de las salidas

cambian de estado maestro hasta el siguiente pulso de reloj. Así que, los estados de biestables en el sistema

pueden cambiarse en forma simultánea durante el mismo pulso de reloj, aun cuando las salidas de los biestables

estén conectadas a entradas de biestable. Esto es posible ya que el nuevo estado aparece en las terminales de

salida solo después de que el pulso de reloj ha regresado a 0. En consecuencia, el contenido del segundo

transferirse al primero, y amabas transferencia pueden ocurrir durante el mismo pulso de reloj.

Biestable disparado por borde. Otro tipo de biestable que sincroniza los cambios de estado durante la transición

de pulsos de reloj es el biestable disparado por borde. En este tipo de biestable, las transiciones de salida ocurren

en un nivel específico del pulso de reloj. Cuando el nivel del pulso de entrada excede el nivel umbral, las entradas

están bloqueadas y, de este modo. El biestable no responde a cambios adicionales en las entradas hasta que el

pulso de reloj regresa a 0 y ocurre otro pulso. Algunos biestable disparados por borde provocan una transición en

el borde positivo del pulso, y otros causan una transición en el borde negativo del pulso.

El diagrama lógico de un biestable tipo disparado por borde positivo se muestra en la figura 57. Consta de tres

biestable básicos del tipo que se muestra. Las compuertas 1 y 2 conforman un biestable básico y las compuertas

3 y 4 conforman otro. El tercer tipo biestable básico que comprende las compuertas 5 y 6 proporciona las salidas

del sistema lógico. Las entradas y del tercer biestable básico deben mantenerse en lógica 1 para que las salidas

permanezcan en sus valores de estado estacionario. Cuando y la salida pasa al estado establecido con

. Cuando y , la salida pasa al estado despejado con . Las entradas y están determinadas

117

mediante los estados de los otros dos biestables básicos. Estos dos biestable básicos responden a las entradas

externas (datos) y (pulso de reloj).

La operación del sistema se explica en la figura 57, donde las compuertas 1-4 vuelven a dibujarse para mostrar

todas sus transiciones posibles. Las salidas y de las compuertas 2 y 3 van a las compuertas 5 y 6 como se

muestra en la figura 57, para proporcionar las salidas reales del biestable. En la figura 57 se muestran los valores

binarios en las salidas de las cuatro compuertas cuando . La entrada puede ser igual a 0 o 1. En

cualquier caso, un de 0 provoca que las salidas de las compuertas 2 y 3 pasen a 1, y asi hacen que ,

que es la condición para una salida de estado estacionario. Cuando , la compuerta 4 tiene una salida 1, la

cual causa que la salida de la compuerta 1 pase a 1. Estas son las dos condiciones posibles cuando el terminal,

que es 0, inhabilita cualesquiera cambios en la salida del biestable, sin importar cuál es el valor de .

Hay un tiempo definido, llamado tiempo de disposición, en el cual la entrada debe mantenerse en un valor

constante antes de la aplicación del pulso. El tiempo de disposición es igual al retardo de propagación a través de

las compuertas 4 y 1, ya que un cambio de provoca un cambio en las salidas de esas dos compuertas. Ahora se

supone que no cambia durante el tiempo de disposición y que la entrada llega a ser 1. Si cuando el

llega a ser 1, entonces permanece en 1 pero cambia a 0. Esto causa que la salida del biestable vaya a 0. Si

ahora mientras hay un cambio en la entrada , la salida de la compuerta 4 permanecerá en 1 (incluso si

va a 1), ya que una de las entradas de compuerta viene de la cual se mantiene en 0. Solo cuando el regresa a

0 puede cambiar la salida de la compuerta 4; pero entonces tanto como vuelven 1, inhabilitando cualquier

cambio en la salida del biestable. Sin embargo, hay un tiempo definido, llamado el tiempo de conservación, en el

que la entrada no debe cambiar después de la aplicación de la transición que va a positivo del pulso. El tiempo

de conservación es igual al retardo de propagación de la compuerta 3, ya que debe asegurarse que se vuelva 0

con objeto de mantener la salida de la compuerta 4 en 1 con independencia del valor de .

Si x cuando entonces cambia a 0, pero permanece en 1, lo cual provoca que las salidas del

biestable vayan a 1. Un cambio de mientras no altera y porque la compuerta 1 se mantiene en 1

por la señal 0 de . Cuando el va a 0, tanto como van a 1 para evitar que la salida tenga cambios.

En resumen, cuando el pulso de reloj de entrada realiza una transición que va a positivo, el valor de se transfiere

a . Los cambios en cuando se mantiene en un valor sostenido de, no afectan . Por otra parte, una

transición del pulso a negativa no afecta la salida, y tampoco cuando .

118

Figura 21. (Árbol sintáctico) Biestable tipo con disparo en borde positivo

&0

0

0

&0

0

0

Q

&0

0

0

&0

0

0

Q

Q'

&0

0

0 0

&0

0

0

D

C

S

R

Fuente: Autor

Siendo así, el biestable disparado por borde elimina cualquier problema de retroalimentación en los sistemas

lógicos secuenciales precisamente como lo hace un biestable maestro-esclavo. El tiempo de disposición y el

tiempo de conservación deben tomarse en consideración cuando se usa este tipo de biestable.

Cuando se usan tipos diferentes de biestable en el mismo sistema secuencial, debe tenerse la seguridad de que

todas las salidas de los biestables hacen sus transiciones al mismo tiempo, esto es, durante ya sea el borde

negativo o el positivo del pulso. Los biestables que se comportan en forma opuesta respecto a la transición de

polaridad adoptada pueden cambiarse con facilidad por la adición de inversores en sus entradas de reloj. Un

procedimiento alterno es proporcionar pulsos positivos y negativos (mediante un inversor), y aplicar entonces

pulsos positivos a los biestables que disparan durante el borde negativo y pulsos negativos a los biestables que

disparan durante el borde positivo, o viceversa.

Entradas directas. Los biestables disponibles en paquetes IC algunas veces proporcionan entradas especiales

para ajustar o despejar el biestable en forma asincrónica. Estas entradas por lo común se llaman preajuste directo y

despeje directo. Afectan el biestable en un valor positivo (o negativo) de la señal de entrada sin la necesidad de un

pulso de reloj. Estas entradas son útiles para producir todos los biestables a un estado inicial antes de su operación

temporizada. Después que se conecta la potencia en un sistema digital, los estados de sus biestables son

119

indeterminados. Un interruptor de despeje limpia todos los biestables a un estado inicial despejado y un

interruptor de inicio principia la operación temporizada del sistema. El interruptor de despeje debe limpiar todos

los biestables en forma asincrónica sin la necesidad de un pulso.

Tabla 9. Biestable con despeje directo

Entradas Salidas Tabla de función

Despeje Reloj

0 0 1

J

Q

Q

K

SET

CLR

C

1 0 0 Sin cambio

1 0 1 0 1

1 1 0 1 0

1 1 1 Lengueta

El símbolo grafico de un biestable maestro-esclavo con despeje directo se muestra en la tabla 22. El reloj o la

entrada tiene un circulo bajo el triangulo pequeño para indicar que las salidas cambian durante la transición

negativa del pulso ( la ausencia de un circulo pequeño indicaría un biestable disparado por borde positivo). La

entrada de despeje directo también tiene un pequeño círculo para indica que, en forma normal, esta entrada debe

mantenerse en 1. Si la entrada de despeje se mantiene en 0, el biestable permanece limpio, independiente de las

otras entradas o del pulso de reloj. La tabla de función específica la operación del sistema lógico. Las son

condiciones no importa que indican que un 0 en la entrada de despeje directo inhabilita todas las demás entradas.

Solo cuando la entrada de despeje es 1 puede tener efecto un transición negativa del reloj en las salidas. Las

salida no cambian si . El biestable cambia o completa cuando . Algunas biestables es posible

que también tengan una entrada de preajuste directo, la cual establece la salida en 1 (y en 0) en forma

asincrónica.

Cuando están disponibles entradas directas asincrónicas en un biestable maestro-esclavo, deben conectarse tanto

al maestro como al esclavo con el objeto de sobrepasar las otras entradas y el reloj. Un despeje directo en al

biestable maestro-esclavo en la figura se conecta a las entradas de las compuertas 1,4 y 8. Un despeje directo

en el biestable disparado en borde en la figura se conecta a las entradas de las compuertas 2 y 6.

Tablas de excitación biestable. Las tablas características de los diversos biestables se presentaron anteriormente.

Una tabla característica define la propiedad lógica del biestable y caracteriza por completo su operación. Los

sistemas lógicos integrados biestables algunas veces se definen por una tabla característica tabulada en forma un

poco diferente. Esta segunda forma de las tablas características para los biestables y se muestra en la

tabla. Representa la misma información que las tablas características en la tabla.

120

En la tabla se define el estado de cada biestable como una función de sus entradas y su estado previo. se

refiere al estado presente al siguiente estado después de la ocurrencia de un pulso de reloj. La tabla

característica para los biestables muestra que el estado siguiente es igual al estado presente cuando tanto la

entrada como la con 0. Cuando la entrada es igual a 1, el siguiente pulso de reloj el biestable. Cuando la

entrada es igual a 1, el siguiente pulso de reloj establece el biestable. El signo de interrogación para el siguiente

estado cuando tanto como son iguales a 1 en forma simultánea designa para el siguiente estado cuando tanto

como son iguales a 1 en forma simultánea designa un estado siguiente indeterminado.

La tabla para el biestable es la misma que para el cuando y se reemplazan por y respectivamente,

excepto para el caso indeterminado. Cuando tanto como son iguales a 1, el estado siguiente es igual al

complemento del estado presente, esto es, = . El estado siguiente del biestable depende por

completo de la entrada y es independiente del estado presente. El siguiente estado del biestable es el mismo

que el estado presente si y se complementa si .

La tabla característica es útil para análisis y para definir la operación del biestable. Especifica el estado siguiente

cuando las entradas del estado presente se conocen. Durante el proceso de diseño, por lo común se conoce la

transición del estado presente al estado siguiente y se desea encontrar las condiciones de entrada del biestable,

que provocaran la transición requerida. Por esta razón, se necesita una tabla que liste las entradas requeridas para

un cambio dado de estado. Dicha lista se denomina tabal de excitación.

En la tabla se presentan las tablas de excitación para los cuatro biestables. Cada tabla consta de dos columnas

y una para cada entrada para mostrar cómo se logra la transición requerida. Hay cuatro transiciones

posibles desde el estado presente al estado siguiente. Las condiciones requeridas de entrada para cada una de las

cuatro transiciones se derivan la información disponible en la tabla característica. El símbolo en las tablas

representa condiciones no importa, esto es, no importa si la entrada es 1 o 0.

Biestable . La tabla de excitación para el biestable se muestra en la tabla. En el primer renglón se muestra

el biestable en el estado 1 en el tiempo Se desea dejarlo en el estado 0 después de la ocurrencia del pulso.

Mediante la tabla característica, se encuentra que si al igual que son 0, el biestable no cambiara de estado. En

consecuencia, tanto la entrada como la deben 0. Sin embargo, en realidad no importa si se hace un 1,

cuando ocurre el pulso, ya que resulta en que deja el biestable en el estado, 0. Por eso puede ser 1 o 0 y el

biestable permanecerá en el estado 0 en . Así, la entrada bajo se marca como condición no importa.

121

Si el biestable está en el estado 0 y se desea que pase al estado 1, entonces mediante la tabla característica, se

encuentra que la única forma de hacer igual a 1 es hacer y . Si el biestable va a tener una

transición del estado 1 al estado 0, debe tenerse y .

La última condición que puede ocurrir es para que el biestable este en el estado 1 y permanezca es el estado 1. Por

supuesto debe ser 0; no se desea despejar el biestable.

Sin embargo, puede ser ya sea un 0 o un 1. Si es 0, el biestable no cambia y permanece en el estado 1; si es un 1,

se establece el biestable en el estado 1, como se desea. Así que, se lista como una condición no importa.

Biestable . La tabla de excitación para el biestable se muestra en la tabla. Cuando tanto el estado presente

como el estado siguiente son 0, la entrada deberá permanecer en 0 y la entrada podrá ser 0 o bien 1. En forma

similar, cuando tanto el estado presente como el siguiente son 1, la entrada debe permanecer en 0 mientras la

entrada puede ser 0 o 1. Si el biestable va a tener una transición del estado 0 al estado 1, debe ser igual a 1 ya

que la entrada establece el biestable. No obstante, la entrada puede ser 0 o en un 1. Si condición la

establece el biestable cuando se requiere; si y el biestable esta complementado y pasa del estado 0 al

estado 1 cuando se requiere. En este caso, la entrada se marca con una condición no importa para la transición

de 0 a 1. Para una transición del estado 1 al estado 0, debe tenerse , ya que la entrada despeja el biestable.

Sin embargo la entrada puede ser 0 o bien 1, ya que no tiene efecto junto con complementa el

biestable con una transición resultante del estado 1 al estado 0.

La tabla de excitación para el biestable ilustra la ventaja de usar este tipo cuando se diseña en sistemas lógicos

secuenciales. El hecho de que tiene muchas condiciones no importa indica que los sistemas lógicos

combinacionales para las funciones de entrada son susceptibles de ser más simples debido a que los términos no

importa por lo común simplifican a una función.

Biestable . La tabla de excitación para el biestable se muestra en la tabla. Mediante la tabla característica, se

observa que el estado siguiente siempre es igual a la entrada y es independiente del estado presente. De este

modo, debe ser 0 si ha de ser 0, y 1 si tiene que ser 1, sin importar el valor de .

Biestable . La tabla de excitación para el biestable se muestra en la tabla. Mediante la tabla características,

tabla, se encuentra que cuando la entrada , el estado del biestable se complementa; cuando el estado

del biestable permanece sin cambio. En consecuencia, cuando el estado del biestable debe permanecer igual, el

requisito es que . Cuando el estado del biestable tiene que complementarse, debe ser igual a 1.

122

Tabla 10. Tablas de excitación biestable

0 0 0 X

0 1 1 0

1 0 0 1

1 1 X 0

0 0 0

0 1 1

1 0 0

1 1 1

0 0 0 X

0 1 1 X

1 0 X 1

1 1 X 0

0 0 0

0 1 1

1 0 1

1 1 0

Otros biestables. El procedimiento de diseño que se describe en este apartado puede usarse con cualquier

biestable. Es necesario conocer la tabla característica del biestable de la cual es posible desarrollar una nueva tabla

de excitación. La tabla de excitación se utiliza entonces para determinas las funciones de entrada del biestable,

como se explica a continuación.

123

ANEXO 12. Lógica Proposicional

12.1 Proposiciones y variables lógicas

La lógica es la herramienta que usan las matemáticas para desarrollarse. El objetivo del mismo es describir en qué

consiste una teoría matemática. Para lograrlo, primero hay que exponer sucintamente las reglas de la lógica de

proposiciones, definir con precisión que es un razonamiento lógico y, por último, explicar en qué consiste su

aplicación en el desarrollo del trabajo de investigación (brevemente, una serie de axiomas, definiciones y

teoremas relacionados entre sí mediante argumentos lógicos usados para sustentar la hipótesis propuesta).

La lógica es un esquema de reglas que permite deducir verdades a partir de otras verdades. El medio que lleva de

las primeras verdades a las otras deducidas se llama razonamiento lógico. La lógica analiza, los razonamientos

lógicos, estableciendo cuando un razonamiento es válido, independientemente del contenido de las verdades que

se enuncien. Solo le interesan las manipulaciones que se hacen con los enunciados, no su contenido.

Todos los resultados mostrados en se prueban rigurosamente. Sin embargo, no se usa para ello el razonamiento

lógico, sino el simple y eficaz camino de las tablas introducidas. Por supuesto, algunos resultados sí se podrían

demostrar a partir de otros anteriores mediante las leyes del algebra de proposiciones, que se exponen. Se prefiere

dejar todo en manos de las tablas, pues en el resto de la investigación son los argumentos lógicos los

protagonistas. Por contra, aunque no se habla de axiomas, definiciones y teoremas en las teorías matemáticas,

desde el principio llamados teoremas a los resultados que se obtuvieren y se podrán visualizar en el anexo

Teoremas.

Proposiciones y variables lógicas. Puesto que la lógica busca deducir verdades a partir de otras verdades, su

materia prima son los enunciados de esas verdades. Eso es lo que se llama proposiciones: un enunciado que se

puede juzgar como verdadero o falso.

Los siguientes enunciados “la máquina está disponible”, “el inventario es suficiente” y “el operario está libre”

son proposiciones, pues se puede juzgar objetivamente que son falsas o verdaderas. Deliberadamente no se escribe

una definición formal del concepto de proposición en nuestra teoría por dos razones. Primero, en muchos casos es

cuestión de opinión si un enunciado se puede juzgar como verdadero o falso, o simplemente, el juicio no será

unánime. La segunda razón es que las proposiciones no son parte de la lógica. Son los ladrillos con los que se

construyen los razonamientos lógicos. La lógica se ocupa de las relaciones entre las proposiciones, no de su

contenido.

124

Es de interés particular, pues, asignar a cada proposición un valor binario, previa validación de la variable de

estado. Por ello se debe usar símbolos que representen proposiciones cualesquiera y examinar las relaciones entre

estos símbolos independientemente de corroborar su registro particular.

Se utilizara letras latinas minúsculas, especialmente . ., para representar proposiciones cualesquiera. La

única característica que nos recuerda que representan proposiciones es que estos símbolos pueden tener dos

valores: verdadero (representado por ) o falso (representado por ). Y como representan proposiciones

cualesquiera, pueden tomar cualquiera de los dos. Estos símbolos no son proposiciones sino variables discretas,

que comúnmente construyen recursivamente las formulas atómicas usadas en la lógica proposicional. Entre estas

variables lógicas discretas para una planta de producción, se definen las materias primas y proceso ( ), equipos

( ), la mano de obra ( ), pertenecientes a cada a centros de trabajo ( ) y productos ( ).

Sin embargo, una vez aclarada la diferencia entre proposiciones y variables lógicas, y puesto que una variable

lógica representa una proposición cualquiera, se empleara los dos términos indistintamente. El análisis utilizando

la lógica va a consistir en analizar variables lógicas y describir las relaciones entre ellas. La relación más sencilla

es la de variables dependientes e independientes. Dos variables lógicas son dependientes si el valor que tome una

condiciona el valor que puede tomar la otra. Son independientes si no son dependientes.

Al representar las variables lógicas por letras como . . Si en una expresión aparecen las variables y

ambas pueden tomar los valores y , y se tiene un total de cuatro combinaciones posibles de los valores de y

. Al tener tres variables, hay ocho posibilidades Una tabla de verdad, o simplemente tabla en este contexto,

es una representación en filas y columnas de los valores de algunas variables lógicas. Cada columna representa

una variable, y cada fila una posible combinación de los valores de las mismas. En la tabla 5 se muestran todas las

posibles combinaciones de los valores y para tres variables.

Una variable lógica puede, en principio, tomar los valores 0 o . Sin embargo, es posible que una variable

dependiente de otras, cuyo valor queda condicionado por estas, tome siempre el valor 1 (verdadero) para cualquier

situación de las variables de las que depende. O bien, otra variable que tome siempre el valor 0 (falso). Las

variables con este comportamiento reciben un nombre. Se llama tautología a la variable lógica, dependiente de

otras, la cual toma el valor 1 independientemente del valor de las variables de las que depende. Análogamente se

llama contradicción a la variable lógica cuyo valor es 0 en cualquier situación.

Tabla 11. Combinaciones de los valores y

p q r

0 0 0

0 0 1

125

0 1 0

0 1 1

1 0 0

1 0 1

1 1 0

1 1 1

12.2 Conectivos lógicos

Los conectores permiten construir nuevas proposiciones a partir de unas dadas. La nueva proposición es

dependiente de las proposiciones con las que se construye. Un conector monario llamado negación el cual, a partir

de una proposición, construye otra. También varios conectores binarios, que a partir de dos proposiciones dan

otra: conjunción, disyunción, implicación y doble implicación. En los cinco casos se dará una explicación intuitiva

seguida de una descripción formal.

La descripción formal consiste en describir exactamente como depende la nueva proposición de las proposiciones

con que se construye. La descripción se hace mediante tablas en las que aparecen todas las combinaciones

posibles de valores que toman las variables independientes. Inicialmente la negación de una proposición, que es

otra proposición con valor opuesto a la primera. Si la primera es cierta, su negación es falsa y viceversa.

En términos de variables lógicas, la negación de una variable es otra variable dependiente de la primera porque su

valor está determinado por el de ella.

La negación de una proposición , denotada , es la proposición cuyo valor es el opuesto al de . Se puede

definir la negación mediante la tabla 6. En ella se indica, para cada valor de la proposición , el valor que toma la

proposición

Tabla 12. Negación de una proposición

0 1

1 0

La conjunción es un conector binario que funciona como la conjunción copulativa “ ” del español. La conjunción

de dos proposiciones, entonces, es una proposición que es cierta si ambas son ciertas, y es falsa si alguna de ellas

es falsa. La conjunción de dos proposiciones denotada es la proposición que solo es cierta si ambas

son ciertas. En un proceso de producción donde las maquinas están dispuestas en serie se podrá expresar en

126

términos de la conjunción. La descripción mediante la tabla 7 consiste ahora en ilustrar, para cada valor que

pueden tomar las proposiciones y el valor que resulta en la proposición

Tabla 13. Conjunción de dos proposiciones denotada

0 0 0

0 1 0

1 0 0

1 1 1

La disyunción es el conector que opera de forma parecida a la conjunción disyuntiva “ ” del español. La

disyunción de dos proposiciones es otra proposición que es cierta si alguna de las dos originales es cierta. Es

decir, basta que una de ellas sea cierta para que la disyunción lo sea. Sin embargo en lógica se emplea en sentido

inclusivo como se aprecia en la tabla que la define. En un proceso de producción donde las maquinas están

dispuestas en paralelo se podrá expresar en términos de la disyunción. La disyunción de dos proposiciones ,

denotada , es la proposición que solo es falsa si ambas son falsas. En forma de tabla 8.

Tabla 14. disyunción de dos proposiciones , denotada

0 0 0

0 1 1

1 0 1

1 1 1

El siguiente conector que se introduce es la implicación, que tiene gran importancia en la lógica pues es la base

del razonamiento deductivo. Requiere un poco de atención para entender bien su descripción formal que, al

principio, no parece responder a la intuición. Cuando se afirma que una proposición implica otra se quiere

expresar el hecho de que si la primera es cierta, entonces la segunda debe ser cierta también.

En el lenguaje corriente se usa la expresión “Si . . . entonces . . . ”. Las dos proposiciones que aparecen en la

implicación se llaman antecedentes y consecuentes. El antecedente es la condición que, si es cierta, asegura que se

cumple el consecuente. Base del lenguaje PWL, la setencia if... Then.. en cualquier lenguaje de

programación.

Decir qué valor tiene la implicación en cada caso de los posibles valores de antecedente y consecuente. Es claro

que quiero decir que una implicación es cierta si el antecedente es cierto y el consecuente también. Por todo ello

127

se define la implicación del siguiente modo. La implicación de dos proposiciones denotada es la

proposición que solo es falsa si es verdadera y es falsa. La tabla 9 correspondiente es:

Tabla 15. La implicación de dos proposiciones denotada

0 0 1

0 1 1

1 0 0

1 1 1

Es fácil convencerse de que la proposición no es la misma que . Esta observación es suficientemente

importante como para asignar nombres a cada una de estas implicaciones.

Dada una implicación , se otorgan nombres a las siguientes implicaciones:

implicación directa,

implicación inversa,

implicación reciproca,

implicación contrapositiva.

El último conector que se introduce es el de doble implicación o bicondiciónal. Como su nombre indica, si dos

proposiciones están relacionadas con el conector doble implicación, significa que una implica la otra y la otra la

una. Entonces, si una de ellas es cierta, la otra debe serlo también, que es lo mismo que decir que si una es falsa la

otra también. La doble implicación de dos proposiciones denotada es la proposición que solo es

verdadera si ambas coinciden en su valor. De la tabla 10 resulta :

Tabla 16. La doble implicación de dos proposiciones denotada

0 0 1

0 1 0

1 0 0

1 1 1

Una explicación que se enuncia a partir de la doble implicación es la de variables lógicas equivalentes. Dos

variables son equivalentes si son dependientes de modo que siempre toman el mismo valor. Si una es verdadera,

entonces la otra también y viceversa. Es claro que el conector de doble implicación puede ayudar a expresar esta

idea. Una forma de hacerlo es decir que la doble implicación entre dos proposiciones equivalentes es siempre

cierta. Dos variables y son equivalentes, y se denota , si es una tautologıa. (Barnes, 1978)

128

Es claro que en cualquier expresión puedo sustituir una proposición por otra equivalente, y la nueva expresión que

obtengo es equivalente a la original pues los valores son los mismos. De ahí que el concepto de proposiciones

equivalentes sea importante y muy utilizado en lógica. Ahora se puede enunciar un primer resultado sencillo pero

muy útil en la teoría y en la práctica de la lógica. Es la relación entre las implicaciones directa, inversa, reciproca

y contrapositiva. Ver anexo Teorema 19.

Otro teorema relacionado con el concepto de equivalencia es la que dice que el conector doble implicación es

equivalente a la implicación directa junto con la implicación inversa. Es la formulación precisa de lo que el

símbolo ↔ expresa abiertamente. Ver anexo Teorema 20.

En las expresiones que incluyen algunos o todos los operadores , en la ausencia de paréntesis, primero se

evalúa después y luego . Esta convención se conoce como precedencia del operador. En álgebra, la

precedencia del operador indica que se evalúan y antes que y –.

12.3 Leyes del algebra proposicional

Los conectores entre proposiciones (negación, conjunción, disyunción, etc.) se pueden ver, desde un punto de

vista algebraico, como operaciones definidas en el conjunto de las proposiciones. Se toma una proposición (en el

caso de la negación) o dos proposiciones (en los otros casos) y se operan, obteniendo como resultado otra

proposición. Resulta imperativo analizar algunas propiedades algebraicas de estas operaciones como son la

aplicación reiterada, asociatividad, conmutatividad, existencia de elemento neutro, etc. (Badesa C, 1998)

Como primer paso se observa que los conectores de implicación y doble implicación se pueden escribir en

términos de la negación, conjunción y disyunción solamente. Entonces bastara con analizar las propiedades

algebraicas de estas tres operaciones. (En realidad, también el conector de disyunción se puede expresar en

función del de conjunción y el de negación, pero estos tres en conjunto tienen más y mejores propiedades

algebraicas. Ver anexo Teorema 21.

Puesto que en el teorema que la doble implicación es equivalente a la implicación directa y la inversa, entonces la

doble implicación también se puede expresar solo con negación, conjunción y disyunción. En definitiva, se darán

uso a las propiedades de la negación, la conjunción y la disyunción.

Propiedades de la negación. Debido a que la negación es una operación monaría, la única propiedad que en este

caso puede analizarse es la aplicación reiterada. El resultado es muy evidente por estar trabajando con

129

proposiciones que solo pueden tomar dos valores. La negación es cambiar el valor de una proposición, y como

solo hay dos posibilidades, si se cambia dos veces se regresa al valor original. Ver anexo Teorema 22.

Propiedades de la conjunción. La conjunción es una operación binaria y en ella sí procede analizar más

propiedades. La idempotencia, da el resultado de operar una proposición consigo misma. La asociatividad nos

indica cómo se puede efectuar la conjunción de tres proposiciones. La conmutatividad muestra que el orden de las

proposiciones en una conjunción es irrelevante. Existe un elemento neutro (la proposición con valor 1, que se

denota simplemente como 1) que al operarlo con cualquier proposición da como resultado la misma proposición.

Existe también un elemento dominante (la proposición con valor 0, que se denota simplemente como 0) que

operado con cualquier proposición arroja el resultado 0. Ver anexo Teorema 23.

La presencia de la propiedad asociativa permite definir el símbolo , sin paréntesis, como o bien

puesto que son iguales. El resultado en ambos casos es que solo es cierto si las tres

proposiciones y son ciertas. Generalizando esta idea se define la conjunción de las variables

denotada como la variable que solo es cierta si todas las variables

son ciertas. Las

propiedades asociativa y conmutativa aseguran que la descripción es coherente con la anterior.

Propiedades de la disyunción. El análisis de la disyunción sigue los mismos pasos que el de la conjunción pues

las propiedades que satisfacen son las mismas. La única diferencia es que los papeles de y , como elementos

neutro y dominante respectivamente, se invierten ahora. Ver anexo Teorema 24.

Las propiedades asociativa y conmutativa aseguran que la explicación es coherente con la descripción de la

disyunción de dos variables.

Propiedades de las operaciones combinadas. Ahora se estudian algunas propiedades que surgen al considerar

expresiones con dos o las tres operaciones combinadas. Ver anexo Teorema 25.

La simplificación de una proposición mediante manipulaciones algebraicas. Cada proposición es equivalente a la

anterior por la ley algebraica que se indica a su lado.

proposición a simplificar

segunda ley de De Morgan

doble negación y conmutatividad

distributividad

complementariedad de la negación

1 neutro de .

130

Prueba algebraica de la ley de absorción (suponiendo probadas las leyes algebraicas anteriores). Partiendo de la

proposición mediante pasos algebraicos se llega a que es equivalente a la proposición .

0 neutro de _

comp. de negación

distributividad

distributividad

idemp. y complemento

distrib., idemp. y dominación

complemento y 1 neutro de ^

0 neutro de .

Cuantificadores. Se introducen los enunciados abiertos y, tras ellos, los cuantificadores. Son elementos muy

habituales en la formulación de definiciones y resultados en matemáticas en expresiones de la forma “para todo

numero entero. . . ” o “existe una función tal que . . . ”.

Se llama abierto a un enunciado que contiene variables que toman valores en un conjunto dado, llamado universo,

de forma que para cada valor que tomen las variables, el enunciado se convierte en una proposición.

Un enunciado abierto no es una proposición por sí mismo, sino que se convierte en una cuando las variables

toman un valor. En el caso anterior, el enunciado puede ser verdadero o falso según los valores que tome la

variable.

Puesto que las proposiciones se representan por letras , los enunciados abiertos se representan por

símbolos como donde son las variables que contiene el enunciado.

Los cuantificadores son unos prefijos que, antepuestos a enunciados abiertos los convierten en proposiciones. Se

utilizan dos: el cuantificador universal y el cuantificador existencial. El primero se simboliza por , y se suele

leer “para todo”. Indica que el enunciado que le sigue debe ser cierto para todos los posibles valores de la

variable. El segundo se simboliza por , y se lee “existe algún”.

Indica que el enunciado que sigue es cierto para, al menos, uno de los valores que puede tomar la variable.

Tomar su propiedad de convertir enunciados abiertos en proposiciones como base para dar una aclaración.

Si es un enunciado abierto que depende de la variable , la cual toma valores en un conjunto universo dado,

definir el símbolo como la proposición que es cierta solo si el enunciado abierto es verdadero para todos

los valores que la variable puede tomar en su universo.

131

c. Se define el símbolo como la proposición que es cierta si el enunciado abierto es verdadero para

algún valor de los que la variable toma en su universo.

d. La proposición no es en realidad otra cosa que una conjunción, mientras que se trata de

una disyunción como se aprecia a continuación.

La necesidad de introducir los cuantificadores aparece cuando los posibles valores de la variable no se pueden

enlistar como en el caso anterior: si ahora toma valores en los numeros reales, no se puede escribir de

otro modo. Para usar cuantificadores basta recordar que un cuantificador junto a un enunciado abierto es una

proposición y, a partir de ahí, se maneja como cualquier otra proposición. Sin embargo hay algunas reglas que

simplifican el uso de proposiciones que contienen cuantificadores. En concreto se analizara dos de ellas: la

negación de proposiciones con cuantificadores y la combinación de cuantificadores. (Enderton, 1972)

Una proposición que comienza con el cuantificador universal necesita que el enunciado abierto sea cierto para

todos los valores de la variable, por tanto basta con que en un valor sea falso para que toda la proposición sea

falsa. Por ello, la negación con un cuantificador universal nos lleva a un cuantificador existencial y viceversa. Al

recordar que es una conjunción y es una disyunción, esto no es otra cosa que las leyes de De

Morgan vistas en el teorema. El resultado preciso se recoge en el siguiente teorema. Ver anexo Teorema 26.

Las primera y segunda reglas nos dicen que combinar cuantificadores universales y combinar cuantificadores

existenciales es conmutativo. Ver anexo Teorema 27.

Gracias a este resultado se puede escribir sin ambigüedad , y o en lugar de , ası como y o

en lugar de , y el orden de las variables e es irrelevante. Sin embargo hay que tener cuidado pues el

orden si es importante cuando se combinan cuantificadores de ambos tipos. (Ershov, 1990)

Para terminar se define el cuantificador de existencia y unicidad, simbolizado . Como su nombre indica este

símbolo contiene dos afirmaciones: primero, la existencia de un elemento que cumple el enunciado; segundo, que

dicho elemento es el único que lo cumple. La forma de enunciar la unicidad es diciendo que si hay dos elementos

que cumplen la propiedad, entonces son iguales. Si es un enunciado abierto, el símbolo es la

proposición definida por

132

TEOREMAS

Teorema 1. Dos conjuntos son iguales si, y solo si, cada uno es subconjunto del otro

Demostración. Primero, la implicación directa. Si entonces, por el axioma todo elemento de es elemento de y

viceversa. Pero, según la definición anterior, esto qué es lo mismo que decir

Segundo, la implicación inversa. Si , entonces todo elemento de esta en y todo elemento de esta

en , lo cual se puede escribir . Pero esta proposición es precisamente el antecedente del axioma, por

lo cual En particular, todo conjunto es subconjunto de sí mismo: .

Teorema 2. El conjunto vacío es subconjunto de cualquier conjunto.

Esto es, si es un conjunto arbitrario,

Demostración. Queremos probar la proposición Pero el antecedente es siempre falso pues, por

definición del conjunto vacío, Entonces la implicación es siempre cierta, independientemente del consecuente,

y el teorema queda probado.

Teorema 3. Dado un conjunto y subconjuntos del mismo

Demostración. Para probar la primera igualdad escribimos la definición de cada miembro y comprobamos que son

iguales:

donde se ha sustituido por su proposición equivalente . Para probar la segunda igualdad basta usar la

definición de diferencia simétrica.

Teorema 4. Sea un conjunto y subconjuntos arbitrarios de el.

Entonces se cumple:

1. Ley del doble complemento:

2. Leyes de idempotencia:

3. Leyes conmutativas:

4. Leyes asociativas:

5. Elementos neutros de la unión y la intersección: el vacío es neutro de la unión y el conjunto E es neutro de la

intersección:

133

6. Elementos dominantes de la unión y la intersección: el conjunto E es dominante en la unión y el vacío lo es en la

intersección:

7. Leyes del complemento:

8. Leyes distributivas:

9. Leyes de absorción:

10. Leyes de De Morgan:

Demostración. Las diecinueve propiedades enunciadas se demuestran similarmente y se pueden trazar hasta las

propiedades equivalentes de proposiciones del apartado anterior. La propiedad del doble complemento no es más que la

propiedad de la doble negación, las propiedades que afectan solo a la unión son exactamente las mismas que las de la

disyunción y las de la intersección aquellas de la conjunción.

Teorema 5. La relación inversa de una equivalencia es ella misma.

equivalencia ⇒

Demostración. En realidad es un resultado más general, pues vale para cualquier relación simétrica. Por ser simétrica,

y para cada pareja también y, por tanto, ambas están en

.

Teorema 6. Sea una equivalencia definida en un conjunto entonces cada elemento del conjunto está en la clase que

representa.

Es decir dos elementos están relacionados si, y solo si, están en la misma clase de equivalencia, es

decir

Demostración. El primer punto es consecuencia inmediata de que toda equivalencia es reflexiva y la definición de clase de

equivalencia. Para el segundo punto, separamos en dos la doble implicación.

Primero veamos que ⇒ demostrando la igualdad de por una doble contención. Si un elemento

c esta en es porque .

Ahora bien, por ser la relación transitiva y tener por hipótesis, entonces se cumple , con lo cual .

Hemos probado Como, además, la relación es simétrica, entonces y el mismo argumento nos lleva a

Por tanto

Teorema 7. Si es una equivalencia en el conjunto , sus clases de equivalencia constituyen una partición de .

Demostración. Debemos probar que las clases de equivalencia verifican las tres condiciones de la definición de partición.

Las clases de equivalencia son, obviamente por su definición, subconjuntos de .

Todo elemento de esta en alguna clase de equivalencia pues, por el teorema anterior, Entonces, es claro que la

union de todas las clases de equivalencia contiene todos los elementos de , y no mas, por el punto anterior.

134

Para probar que clases de equivalencia diferentes son disjuntas nos fijamos en la contrapositiva: si tienen un elemento en

común, entonces son iguales.

Teorema 8. Dada una partición de un conjunto, existe una equivalencia definida en dicho conjunto cuyas clases de

equivalencia son los subconjuntos que constituyen la partición.

Demostración. Sea el conjunto en el que hay definida una partición. Definamos en la relación de modo que dados

dos elementos , a esta relacionado con si a esta en el mismo subconjunto de la partición que .

Primero veamos que esta relación es una equivalencia. Es reflexiva, pues, obviamente, cualquier elemento esta en el

mismo subconjunto que el mismo. Es simétrica, pues si a esta en el mismo subconjunto que , entonces esta en el

mismo subconjunto que a. Es transitiva, pues si significa que tanto a como c están en el mismo subconjunto

que solo puede estar en uno, ya que los subconjuntos de una partición son disjuntos. Entonces están en el

mismo subconjunto y por tanto .

Teorema 9. La relación inversa de un orden es también un orden, denominado orden inverso.

Demostración. Sea un orden. Por ser asimétrica es claro que también lo es. Veamos que también es transitiva. Si

y es porque . Entonces, por ser R transitiva, , luego

.

La estructura que impone un orden en un conjunto hace destacar algunos elementos del mismo, un elemento que sea

mayor que todos los demás, un máximo; o un elemento que, aunque no sea mayor que todos los demás, no tenga a nadie

por encima de él, un maximal. Veamos con detalle todos estos elementos destacados. En las siguientes definiciones

asumimos que es un conjunto ordenado.

Teorema 10. Todo elemento máximo es maximal y, si existe, el máximo es único.

Análogamente, todo elemento mínimo es minimal y, si existe, es único.

Demostración. Probamos la parte del máximo, pues la del mínimo es similar.

Si es máximo entonces para cualquier en el conjunto.

Si se da la primera instancia, es claro que , por la propiedad asimétrica del orden.

Si se da la segunda, de nuevo tenemos a , pues de lo contrario también se violaría la propiedad asimétrica. Por

tanto es maximal.

Teorema 11. Un subconjunto acotado superiormente tiene máximo si, y solo si, tiene supremo y este pertenece a dicho

subconjunto.

Un subconjunto acotado inferiormente tiene mínimo si, y solo si, tiene ínfimo y este pertenece a dicho subconjunto.

Demostración. Probamos la relación entre máximo y supremo, pues la otra es similar. Primero la implicación directa. Sea

el máximo de . Entonces para todo elemento en , por tanto, b es una cota superior de . Ahora sea c otra

cota superior de . Entonces, como b esta en tenemos , luego es mínimo del conjunto de cotas superiores, es

decir, b es el supremo de .

Ahora la implicación inversa. Sea el supremo de B, el cual cumple además . Por ser supremo es cota superior,

luego todo elemento de cumple . Entonces b cumple la definición de máximo de

Teorema 12. En un orden total todo maximal es máximo y, por tanto, único y todo minimal es mínimo y, por tanto, único.

Demostración. Sea a un elemento maximal, y sea x un elemento arbitrario. Por ser a maximal tenemos a pero, por

ser el orden total, son comparables, luego debe ser , de donde a es máximo.

135

Los cuatro conjuntos numéricos aludidos, a pesar de ser todos órdenes totales, tienen propiedades que diferencian sus

estructuras de orden. En los próximos párrafos vamos a describir las propiedades que diferencian cada uno de los cuatro

órdenes (algunas de estas propiedades no son exclusivas de los órdenes totales, pero hemos preferido enunciarlas aquí

para aplicarlas directamente al caso de los conjuntos numéricos).

La primera propiedad es la del buen orden, y diferencia a los naturales de los otros conjuntos.

Teorema 13. En un conjunto con más de un elemento, si un orden total es lineal, entonces no verifica las propiedades del

inmediato sucesor ni del inmediato antecesor.

Demostración. Probamos su contrapositiva, que es equivalente: si se cumple la propiedad del inmediato sucesor o del

inmediato antecesor, entonces no es lineal.

Efectivamente, sea un elemento que no es máximo (existe porque el conjunto tiene más de un elemento) y sea y su

inmediato sucesor (con el antecesor es similar). Por definición de inmediato sucesor no existe un tal que ,

luego el orden no es lineal.

Teorema 14. Un orden total verifica la propiedad del supremo si, y solo si, verifica la propiedad del ínfimo.

Demostración. Supongamos que un orden total satisface la propiedad del supremo.

Sea un subconjunto acotado inferiormente y consideremos el conjunto de las cotas inferiores de dicho subconjunto.

Claramente este conjunto esta acotado superiormente y, por hipótesis, tiene supremo. Es fácil ver que el supremo de las

cotas inferiores es el ínfimo del subconjunto original. Por tanto se satisface la propiedad del ínfimo. Igualmente se razona

a la inversa probando así la equivalencia.

Teorema 15. Ordenación por comparación

Cualquier algoritmo que ordena por comparación de claves y elimina cuando más una inversión después de cada

comparación deberá efectuar al menos comparaciones en el peor caso y al menos comparaciones

en promedio (con elementos).

Teorema 16. no es un lenguaje recursivamente enumerable.

Es decir, no existe ninguna máquina de Turing que acepte .

Demostración. Supongamos que fuera para alguna . Dado que es un lenguaje sobre el alfabeto

debería estar en la lista de máquinas de Turing que hemos construido, dado que incluye todas las cuyo alfabeto de

entrada es Por tanto, existe al menos un código para , por ejemplo ; es decir,

Ahora veamos si pertenece a .

Si pertenece a , entonces acepta Pero entonces, por definición de , wi no pertenece a , porque

sólo contiene aquellas wj tales que no acepta .

De manera similar, si no pertenece a , entonces no acepta . Por tanto, por definición de , pertenece a .

Dado que no puede simultáneamente pertenecer a y no pertenecer a , concluimos que existe una contradicción en

la suposición de que existe Es decir, no es un lenguaje recursivamente enumerable.

Teorema 17. Si es un lenguaje recursivo, entonces también lo es.

Demostración. Sea para alguna que siempre se para. Construimos una tal que de

acuerdo con la construcción sugerida. Es decir, : se comporta igual que . Sin embargo, se modifica como sigue

para crear :

Los estados de aceptación de se convierten en los estados de no aceptación de sin transiciones; es decir, en estos

estados, se parará sin aceptar.

136

tiene un nuevo estado de aceptación . Desde no existen transiciones.

Para cada combinación de un estado de no aceptación de y un símbolo de cinta de tal que no tiene transiciones (es

decir, se para sin aceptar), se añade una transición al estado de aceptación .

Dado que está garantizado que siempre se para, sabemos que también está garantizado que se parará.

Además, acepta exactamente aquellas cadenas que no acepta. Por tanto, acepta

Teorema 18. Si existe una reducción de a

Entonces:

a. Si es indecidible, entonces también lo es.

xxxxxxxxxxx

b. Si es , entonces también lo es.

Demostración. En primer lugar, suponemos que es indecidible. Si es posible decidir sobre , entonces podemos

combinar la reducción de a con el algoritmo que decide sobre para construir un algoritmo que decida sobre .

Más detalladamente, suponemos que disponemos de un caso de . Aplicamos a el algoritmo que convierte en un

caso de . A continuación aplicamos el algoritmo que decide sobre a . Si dicho algoritmo da como respuesta “sí”,

entonces x está en . Dado que hemos reducido a , sabemos que la respuesta de a es “sí”; es decir,

pertenece a . Igualmente, si no forma parte de entonces no forma parte de , y lo que responda a la cuestión

“¿está x en ?” será también la respuesta correcta a “¿está en ?”

Por tanto, hemos llegado a una contradicción de la suposición de que es indecidible. La conclusión es que si es

indecidible, entonces , también es lo es.

Consideremos ahora el apartado (b). Supongamos que es , pero es . Ahora tenemos un algoritmo para

reducir a , pero sólo disponemos de un procedimiento para reconocer ; es decir, existe una que da como

respuesta “sí” si su entrada pertenece a , pero puede no pararse si su entrada no pertenece a . Como en el apartado

(a), partimos de una instancia de , la convertimos mediante el algoritmo de reducción en una instancia de . Luego

aplicamos la para a . Si se acepta, entonces se acepta.

Teorema 19. Las implicaciones directa y contrapositiva son equivalentes, y las implicaciones inversa y reciproca son

equivalentes.

Simbólicamente

Demostración. Probamos la primera equivalencia, pues la otra es similar. Para ello basta con elaborar una tabla con todos

los casos posibles y ver que, efectivamente, en todos ellos las proposiciones directa y contrapositiva toman el mismo

valor. Obsérvese que las columnas y son auxiliares en esta tabla, pues el objetivo es comparar las columnas

etiquetadas como

0 0 1 1 1 1

0 1 1 0 1 1

1 0 0 1 0 0

1 1 0 0 1 1

Por tanto, de la tabla anterior construimos la siguiente

Tabla 17. Relación entre las implicaciones directa, inversa, reciproca y contrapositiva.

137

0 0 1

0 1 1

1 0 1

1 1 1

donde se ve que la bicondiciónal es una tautología, pues en cualquiera de los cuatro casos el resultado es la constante .

Teorema 20. La doble implicación es equivalente a la conjunción de las implicaciones directa e inversa.

Es decir,

Demostración. Como antes, basta elaborar las tablas de ambas proposiciones y comprobar que sus resultados son iguales

para todos los valores posibles de y . En este caso las dos últimas columnas deben ser iguales, mientras que las

columnas son auxiliares.

Tabla 18. La doble implicación

0 0 1 1 1 1

0 1 1 0 0 0

1 0 0 1 0 0

1 1 1 1 1 1

Por ser la doble implicación como dos implicaciones, se acostumbra a leer también con la formula “ si, y solo

si, ” .

Teorema 21. La implicación de dos proposiciones es equivalente a la disyunción de la negación de la primera con la

segunda.

Demostración. Construimos las tablas de ambas con la columna auxiliar

Tabla 19. La implicación de dos proposiciones

0 0 1 1 1

0 1 1 1 1

1 0 0 0 0

1 1 0 1 1

La coincidencia de las dos últimas columnas en todos los casos demuestra que ambas proposiciones son equivalentes. Por

tanto, en cualquier expresión podemos sustituir por y viceversa.

Teorema 22. La negación de la negación es equivalente a la proposición original.

138

Es decir,

Demostración. Construimos una tabla

Tabla 20. La negación de la negación

0 1 0

1 0 1

Puesto que la primera y la última columna son iguales, las variables que representan son equivalentes.

Teorema 23. Conjunción de proposiciones satisface las propiedades de idempotencia, asociatividad, conmutatividad,

existencia de un elemento neutro y de un elemento dominante

Simbólicamente, si y son proposiciones cualesquiera se cumple

1. Idempotencia:

2. Asociatividad:

3. Conmutatividad:

4. Elemento neutro (1):

5. Dominación (por 0):

Demostración. La idempotencia está demostrada en la misma definición de la operación , (definición 1.8) pues en ella se

aprecia que 1

En la tabla también se prueba la conmutatividad. Asimismo se ve que 1 sirve como neutro y que 0 operado con cualquier

otro valor resulta en 0. Entonces solo resta probar la propiedad asociativa. Construimos una tabla de las proposiciones

La igualdad de las dos últimas columnas prueba que ambas proposiciones son equivalentes.

Teorema 24. La disyunción de proposiciones satisface las propiedades de idempotencia, asociatividad, conmutatividad,

existencia de un elemento neutro y de un elemento dominante.

Es decir, si y son proposiciones cualesquiera, se cumple

1. Idempotencia:

139

2. Asociatividad:

3. Conmutatividad:

4. Elemento neutro (0):

5. Dominación (por 1):

Demostración. La idempotencia está demostrada en la misma definición de la operación , (definición 1.10) pues en ella

se aprecia que 1 En la tabla también se prueba la conmutatividad. Asimismo se ve que la

constante 0 sirve como neutro y que la constante 1 operada con cualquier otro valor resulta en 1. Entonces solo resta

probar la propiedad asociativa. Construimos una tabla de las proposiciones

Como en el caso de la conjunción podemos definir el símbolo como o bien puesto que son

iguales. El resultado es que es cierta si alguna de las tres es cierta, o bien, es falsa solo si todas son falsas.

Generalizando esta idea definimos la disyunción de las variables denotada como la

variable que solo es falsa si todas las variables son falsas.

Teorema 25. Las siguientes relaciones son validas para cualesquiera proposiciones

1. Complementariedad de la negación:

2. Leyes distributivas:

3. Absorción:

4. Leyes de De Morgan:

Demostración. La complementariedad de la negación se prueba en la siguiente tabla.

La prueba de las propiedades distributivas sigue en una tabla de ocho filas.

La igualdad de la cuarta y quinta columnas es la prueba de la distribución de respecto a _, mientras que la sexta y

séptima columnas prueban la otra distribución.

140

En una ultima tabla se prueban las propiedades de absorción (tercera y cuarta columnas que son iguales a la primera) y las

leyes de De Morgan (quinta y sexta columnas, primera ley, séptima y octava, segunda ley).

Las leyes demostradas permiten hacer manipulaciones algebraicas con las proposiciones y probar algunos resultados sin

necesidad de recurrir a las tablas.

Teorema 26. Si es un enunciado abierto, con una variable, entonces se cumplen las equivalencias

Demostración. Como se ha dicho, se trata de las leyes de De Morgan. Razonemos una de ellas como muestra. La negación

de la proposición es cierta si el enunciado no se cumple en algun valor de la variable. Pero eso es

precisamente lo que dice la proposición

Si un enunciado abierto contiene varias variables, se necesita un cuantificador para cada una. Así, si es un

enunciado abierto con las variables e , entonces son enunciados abiertos con una variable: y.

Pero son proposiciones. La combinación de varios cuantificadores tiene algunas reglas que

permiten simplificar su escritura, pero requiere atención pues no todos los casos son simplificables.

Teorema 27. Si es un enunciado abierto que depende de dos variables, se cumplen las siguientes equivalencias

entre proposiciones.

Demostración. La proposición solo es verdadera si dado cualquier , puedo elegir cualquier y obtengo

que es verdadero. Pero en tal caso el valor de y elegido es independiente de , y puedo escogerlo primero.

Entonces, dado cualquier y, puedo elegir cualquier y tendré verdadero, lo cual es la proposición

Con esto se ha probado que cuando la primera es cierta, la segunda también. El mismo razonamiento pero a la inversa

muestra que cuando la segunda es cierta la primera también. En total ambas tienen siempre el mismo valor y, por tanto,

son equivalentes.

Análogamente la proposición afirma que existe algún de modo que puedo encontrar una y tal que

es verdadero. Puedo tomar los valores en orden inverso: escoger primero el valor de y encontrado antes, luego

cierta, entonces también lo es. El mismo razonamiento se aplica a la inversa y llegamos a que ambas son

equivalentes.

Teorema 28. Para proposiciones cualesquiera los siguientes son razonamientos lógicos

1. Modus ponendo ponens:

141

2. Modus tollendo tollens:

3. Silogismo:

4. Demostración por contradicción:

5. Demostración por casos:

6. Silogismo disyuntivo:

7. Conjunción:

8. Simplificación conjuntiva:

9. Amplificación disyuntiva:

10. Especificación universal: con a un elemento cualquiera del universo de

11. Generalización universal: (p(a) (a es arbitrario)) )

12. Especificación existencial: con a el elemento al que se refiere la existencia.

Demostración. Todas estas reglas de inferencia se pueden probar elaborando la tabla correspondiente, pero también

mediante manipulaciones algebraicas. En cualquier caso son todas muy similares, por lo cual expondremos la prueba de

tres de ellas con todo detalle, a modo de muestra, dejando el resto como ejercicio.

Prueba del modus ponendo ponens mediante una tabla. Para probar debemos probar que

es una tautologıa. Construimos la tabla con todos los ingredientes de esta última expresión.

La última columna muestra que, efectivamente, la implicación es una tautología y por tanto el razonamiento es válido.

Prueba del razonamiento por contradicción mediante manipulaciones algebraicas.

Para probar que la implicación es un razonamiento, debo probar que es equivalente a la proposición 1

(tautología) mediante una cadena de proposiciones equivalentes entre sí. En cada paso se da la razón que lo justifica.

(por la equivalencia )

(doble negación)

(0 neutro de )

(complementariedad de la negación).

Por último, la prueba de uno de los razonamientos que involucran cuantificadores y enunciados abiertos. Probamos el

razonamiento de especificación universal usando uno de los razonamientos lógicos de este mismo teorema, supuesto ya

demostrado. La proposición es equivalente a la conjunción de la proposición cuando x toma todos los

valores posibles. Entonces, por la regla de simplificación conjuntiva, de la premisa deducimos que cualquiera de las

proposiciones es cierta, en particular, si a es un valor posible de es cierta.

142

GLOSARIO

Autómatas finitos. Los autómatas finitos utilizan estados y transiciones entre estados en respuesta a las entradas. Resultan

útiles para construir diversos tipos de software, incluyendo el componente de análisis léxico de un compilador y los

sistemas que permiten verificar la corrección de, sistemas lógicos o protocolos.

Autómata finito determinista. Un AFDtiene un conjunto finito de estados y un conjunto finito de símbolos de entrada. Un

estado se diseña para que sea el estado inicial, y cero o más estados para que sean estados de aceptación. Una función de

transición determina cómo cambia el estado cada vez que se procesa un símbolo de entrada.

Diagramas de transiciones. Son adecuados para representar autómatas mediante un grafo en el que los nodos son los estados

y los arcos se etiquetan con los símbolos de entrada, indicando las transiciones de dicho autómata. El estado inicial se

designa mediante una flecha y los estados de aceptación mediante círculos dobles.

Lenguaje de un autómata. El autómata acepta cadenas. Una cadena es aceptada si, comenzando por el estado inicial, la

transición causada por el procesamiento de los símbolos de dicha cadena, uno cada vez, lleva a un estado de aceptación.

En términos del diagrama de transiciones, una cadena es aceptada si sus símbolos son las etiquetas de un camino que va

desde el estado inicial hasta algún estado de aceptación.

Autómata finito no determinista. El AFN difiere del AFD en que el primero puede tener cualquier número de transiciones

(incluyendo cero) a los estados siguientes desde un estado dado para un determinado símbolo de entrada.

Construcción de subconjuntos. Si se tratan los conjuntos de un AFN como estados de un AFD, es posible convertir

cualquier AFN en un AFD que acepta el mismo lenguaje.

Transiciones-ε . Podemos extender el AFN permitiendo transiciones para una entrada vacía, es decir, para ningún símbolo de

entrada. Estos AFN extendidos puede convertirse en autómatas AFD que aceptan el mismo lenguaje.

Aplicaciones de búsquedas en texto. Los autómatas finitos no deterministas son una forma útil de representar reconocedores

de patrones que exploran un texto largo para localizar una o más palabras clave. Estos autómatas pueden simularse

directamente por software o pueden convertirse primero en un AFD, que a continuación se simula.

Alfabetos. Un alfabeto es cualquier conjunto finito de símbolos.

Cadenas de caracteres. Una cadena es una secuencia de símbolos de longitud finita.

Lenguajes y problemas. Un lenguaje es un conjunto (posiblemente infinito) de cadenas, donde los símbolos símbolo de

todas ellas se han seleccionado de un determinado alfabeto. Cuando las cadenas de un lenguaje se interpretan de alguna

manera, la cuestión de si una cadena pertenece o no al lenguaje se dice, en ocasiones, que es un problema.

Máquina de Turing. La máquina de Turing es una máquina de computación abstracta con la potencia tanto de las

computadoras reales como de otras definiciones matemáticas de lo que se puede calcular. La MT consta de una unidad de

control y de una cinta infinita dividida en casillas. Cada casilla almacena uno de los símbolos del conjunto finito de

símbolos de cinta y una casilla corresponde a la posición actual de la cabeza de la cinta. La MT realiza movimientos

basados en su estado actual y en el símbolo de cinta de la casilla a la que apunta la cabeza de la cinta. En un movimiento,

cambia el estado, sobreescribe la celda señalada por la cabeza con algún símbolo de cinta y mueve la cabeza una celda

hacia la izquierda o hacia la derecha.

Son autómatas que modelan la potencia de las computadoras reales. Nos permiten analizar la decidibilidad, es decir, el

problema de qué puede o no puede hacer una computadora. También nos permiten distinguir los problemas tratables

(aquellos que pueden resolverse en un tiempo polinómico) de los problemas intratables (los que no se pueden resolver en

un tiempo polinómico).

Aceptación en una máquina de Turing. Inicialmente, la MT tiene en la cinta su entrada, una cadena de longitud finita de

símbolos de cinta, y el resto de las casillas contienen un espacio en blanco. Este último es uno de los símbolos de cinta y

la entrada se selecciona de un subconjunto de los símbolos de cinta que no incluye el espacio en blanco, y se conocen

como símbolos de entrada. La MT acepta su entrada si llega a un estado de aceptación.

143

Lenguajes recursivamente enumerables. Los lenguajes aceptados por la MT son los denominados lenguajes

recursivamente enumerables (RE). Por tanto, los lenguajes RE son aquellos lenguajes que pueden ser reconocidos o

aceptados por cualquier clase de dispositivos de computación.

Máquinas de Turing no deterministas. La MTN tiene un número finito de posibilidades para realizar el siguiente

movimiento (estado, nuevo símbolo y movimiento de la cabeza) para cada estado y símbolo señalado. Acepta una entrada

si cualquier secuencia de elecciones lleva a una configuración que corresponde a un estado de aceptación. Aunque

aparentemente más potente que la MT determinista, la MTN no es capaz de reconocer ningún lenguaje que no sea

recursivamente enumerable.

Simulación de una máquina de Turing mediante una computadora real. En principio, es posible, simular una máquina de

Turing mediante una computadora real si aceptamos que existe un suministro potencialmente infinito de un dispositivo de

almacenamiento extraíble, un disco, para simular la parte en que no hay espacios en blanco de la cinta de la MT. Puesto

que los recursos físicos con los que se construyen los discos no son infinitos, este argumento es cuestionable. Sin

embargo, dado que la cantidad de dispositivos de almacenamiento que existe en el universo es desconocida y, sin duda,

muy grande, la suposición de que existen recursos infinitos, como en una cinta de una MT, es realista en la práctica y

generalmente se acepta.

Simulación de una computadora mediante una máquina de Turing. Una máquina de Turing puede simular el

almacenamiento y la unidad de control de una computadora real empleando una cinta para almacenar todas las posiciones

y los contenidos correspondientes a los registros, la memoria principal, los discos y otros dispositivos de almacenamiento.

Por tanto, podemos estar seguros de que algo que una máquina de Turing no pueda hacer, tampoco lo podrá hacer una

computadora real.

Lenguajes recursivos y recursivamente enumerables. Los lenguajes aceptados por lasmáquinas de Turing son

recursivamente enumerables (RE) y el subconjunto de los lenguajes RE que son aceptados por una MT que siempre se

para se denominan lenguajes recursivos.

Decidibilidad e indecidibilidad. “Decidible” es sinónimo de “recursivo”, aunque se suele decir que los lenguajes son

“recursivos” y los problemas (que son lenguajes interpretados como una cuestión) son “decidibles”. Si un lenguaje no es

recursivo, entonces decimos que el problema expresado por dicho lenguaje es “indecidible”.

El lenguaje . Este lenguaje es el conjunto de cadenas de ceros y unos que, cuando se interpretan como una MT, no forman

parte del lenguaje de dicha MT. El lenguaje es un buen caso de un lenguaje que no es RE; es decir, que ninguna

máquina de Turing acepta.

El lenguaje universal. El lenguaje Lu está formado por cadenas que se interpretan como la codificación de una MT seguida

de una entrada para dicha MT. La cadena pertenece a si la MT acepta dicha entrada. es un buen caso de un

lenguaje que es RE pero no recursivo.

Reduccciones en tiempo polinómico. Si podemos transformar casos de un problema en tiempo polinómico en casos de un

segundo problema que proporciona la misma respuesta (sí o no), entonces decimos que el primer problema es reducible

en tiempo polinómico al segundo.

Problemas NP-completos. Un lenguaje es NP-completo si pertenece a NP, y existe una reducción en tiempo polinómico de

cada uno de los lenguajes de NP al lenguaje en cuestión. Estamos casi seguros de que ninguno de los problemas NP-

completos pertenece a P, y el hecho de que nadie haya encontrado un algoritmo en tiempo polinómico para ninguno de los

miles de problemas NP-completos conocidos refuerza la evidencia de que ninguno de ellos está en P.

Problemas de satisfacibilidad NP-completos. El teorema de Cook demostró el primer problema NPcompleto (si una expresión booleana

es satisfacible) reduciendo todos los problemas en NP al problema SAT en tiempo polinómico. Además, el problema sigue siendo NP-

completo incluso aunque la expresión se restrinja a un producto de cláusulas, estando cada una de estas cláusulas formada sólo por tres

literales: el problema 3SAT.