Un lenguaje de programación es un conjunto de reglas sintácticas y semánticas que permiten expresar instrucciones que una máquina puede interpretar o ejecutar. Actúan como puente entre el pensamiento humano y la operación de la máquina.
| Nivel | Tipo | Ejemplo |
|---|---|---|
| Bajo nivel | Lenguaje máquina (binario) | 10110000 01100001 |
| Bajo nivel | Ensamblador (Assembly) | MOV AL, 61h |
| Alto nivel | Lenguajes estructurados/OOP | C, Java, Python, Pascal |
Por paradigma:
Por generación:
| Generación | Descripción | Ejemplo |
|---|---|---|
| 1ª GL | Lenguaje máquina | Binario |
| 2ª GL | Ensamblador | Assembly |
| 3ª GL | Lenguajes procedurales de alto nivel | C, Pascal, COBOL |
| 4ª GL | Orientados a aplicaciones/bases de datos | SQL, ABAP |
| 5ª GL | Inteligencia artificial y lógica | Prolog, Mercury |
Diferencia clave (oposición): El compilador produce un ejecutable independiente; el intérprete necesita estar presente en tiempo de ejecución.
Código fuente
↓
[Análisis Léxico] → Tokens
↓
[Análisis Sintáctico] → Árbol de Análisis (AST)
↓
[Análisis Semántico] → Tabla de símbolos
↓
[Generación de Código Intermedio]
↓
[Optimización]
↓
[Generación de Código Máquina]
↓
Ejecutable (.exe / binario)
Un tipo de dato define el conjunto de valores que puede tomar una variable y las operaciones que pueden realizarse sobre ella.
Representa números sin parte decimal.
| Tipo | Bits | Rango (sin signo) | Ejemplo |
|---|---|---|---|
| byte | 8 | 0 a 255 | byte b = 200; |
| short | 16 | -32.768 a 32.767 | short s = 1000; |
| int | 32 | -2.147M a 2.147M | int i = 42; |
| long | 64 | -9.2×10¹⁸ a 9.2×10¹⁸ | long l = 9999999999L; |
Representación interna: complemento a dos (permite representar negativos).
Ejemplo: -5 en 8 bits (complemento a 2)
5 en binario = 00000101
Invertir bits = 11111010
Sumar 1 = 11111011 → Esto es -5
Representa números con parte decimal. Se usa el estándar IEEE 754.
| Tipo | Bits | Precisión |
|---|---|---|
| float | 32 | ~7 dígitos decimales |
| double | 64 | ~15 dígitos decimales |
Estructura IEEE 754 (float, 32 bits):
[1 bit signo | 8 bits exponente | 23 bits mantisa]
Representa un único carácter. Usa codificación ASCII (7/8 bits, 128/256 caracteres) o Unicode/UTF-8 (hasta 4 bytes, millones de caracteres).
ASCII: 'A' = 65, 'a' = 97, '0' = 48
Char en C: char c = 'A'; // almacena el valor 65
Solo dos valores: true (verdadero) o false (falso). Internamente se representa con 1 bit (o 1 byte por eficiencia).
boolean activo = true;
boolean terminado = false;
// Enum en C
enum DiaSemana { LUNES, MARTES, MIERCOLES, JUEVES, VIERNES, SABADO, DOMINGO };
enum DiaSemana hoy = MIERCOLES; // hoy vale 2 (empieza en 0)
// Puntero en C
int x = 10;
int *ptr = &x; // ptr apunta a la dirección de x
printf("%d", *ptr); // imprime 10 (desreferencia)
int i = 100;
long l = i; // automático: int → long
double d = 9.99;
int i = (int) d; // i = 9 (se trunca)
| Operador | Operación | Ejemplo | Resultado |
|---|---|---|---|
+ |
Suma | 5 + 3 |
8 |
- |
Resta | 5 - 3 |
2 |
* |
Multiplicación | 5 * 3 |
15 |
/ |
División | 7 / 2 |
3 (enteros) / 3.5 (reales) |
% |
Módulo (resto) | 7 % 3 |
1 |
** o ^ |
Potencia | 2 ** 3 |
8 |
Importante (oposición): En división entera,
7 / 2 = 3(se trunca). Para obtener 3.5 hay que usar7.0 / 2o hacer casting.
Devuelven un valor booleano (true/false).
| Operador | Significado | Ejemplo | Resultado |
|---|---|---|---|
== |
Igual a | 5 == 5 |
true |
!= |
Distinto de | 5 != 3 |
true |
> |
Mayor que | 5 > 3 |
true |
< |
Menor que | 3 < 5 |
true |
>= |
Mayor o igual | 5 >= 5 |
true |
<= |
Menor o igual | 3 <= 4 |
true |
| Operador | Operación | Descripción |
|---|---|---|
&& / AND |
Conjunción | true solo si ambos son true |
\|\| / OR |
Disyunción | true si al menos uno es true |
! / NOT |
Negación | Invierte el valor booleano |
XOR |
Disyunción exclusiva | true si exactamente uno es true |
Tablas de verdad:
AND: OR: NOT:
A B A&&B A B A||B A !A
T T T T T T T F
T F F T F T F T
F T F F T T
F F F F F F
| Operador | Equivale a | Ejemplo |
|---|---|---|
= |
Asignación simple | x = 5 |
+= |
x = x + n |
x += 3 |
-= |
x = x - n |
x -= 3 |
*= |
x = x * n |
x *= 2 |
/= |
x = x / n |
x /= 2 |
%= |
x = x % n |
x %= 3 |
int x = 5;
x++; // Post-incremento: usa x (=5) luego suma 1 → x=6
++x; // Pre-incremento: suma 1 primero → x=7, usa x (=7)
x--; // Post-decremento
--x; // Pre-decremento
| Operador | Operación | Ejemplo (4 bits) |
|---|---|---|
& |
AND bit a bit | 1010 & 1100 = 1000 |
\| |
OR bit a bit | 1010 \| 1100 = 1110 |
^ |
XOR bit a bit | 1010 ^ 1100 = 0110 |
~ |
NOT bit a bit | ~1010 = 0101 |
<< |
Desplazamiento izquierda | 0001 << 2 = 0100 (×4) |
>> |
Desplazamiento derecha | 1000 >> 2 = 0010 (÷4) |
1. () → Paréntesis
2. ! ~ ++ -- → Unarios
3. * / % → Multiplicativos
4. + - → Aditivos
5. << >> → Desplazamiento
6. < <= > >= → Relacionales
7. == != → Igualdad
8. & → AND bit a bit
9. ^ → XOR bit a bit
10. | → OR bit a bit
11. && → AND lógico
12. || → OR lógico
13. ?: → Ternario
14. = += -= → Asignación
Las instrucciones condicionales permiten alterar el flujo de ejecución del programa en función de si una condición es verdadera o falsa.
Sintaxis general (pseudocódigo):
SI condición ENTONCES
instrucciones
SINO SI condición2 ENTONCES
instrucciones
SINO
instrucciones
FIN SI
En Java/C:
int nota = 7;
if (nota >= 9) {
System.out.println("Sobresaliente");
} else if (nota >= 7) {
System.out.println("Notable");
} else if (nota >= 5) {
System.out.println("Aprobado");
} else {
System.out.println("Suspenso");
}
// Salida: Notable
En Python:
nota = 7
if nota >= 9:
print("Sobresaliente")
elif nota >= 7:
print("Notable")
elif nota >= 5:
print("Aprobado")
else:
print("Suspenso")
Alternativa al if-else encadenado cuando se compara una variable contra múltiples valores constantes.
// Java
int dia = 3;
switch (dia) {
case 1:
System.out.println("Lunes");
break;
case 2:
System.out.println("Martes");
break;
case 3:
System.out.println("Miércoles");
break;
default:
System.out.println("Otro día");
}
// Salida: Miércoles
Importante: Sin
break, el flujo "cae" al siguiente caso (fall-through). En las oposiciones es un error frecuente.
// Pseudocódigo
SEGUN variable HACER
CASO valor1: instrucciones
CASO valor2: instrucciones
POR DEFECTO: instrucciones
FIN SEGUN
Forma compacta de un if-else simple:
// condicion ? valor_si_true : valor_si_false
int max = (a > b) ? a : b;
String estado = (activo) ? "Activo" : "Inactivo";
// Si (a > 0) es false, NO se evalúa (b / a)
// Esto evita división por cero
if (a > 0 && b / a > 2) { ... }
// Si (x != null) es false, NO se evalúa x.length()
// Esto evita NullPointerException
if (x != null && x.length() > 0) { ... }
Un bucle (o ciclo) permite ejecutar un bloque de instrucciones repetidamente mientras se cumpla una condición.
Elementos de un bucle:
- Inicialización: valor de partida del contador/variable de control.
- Condición: expresión booleana que determina si el bucle continúa.
- Actualización: modificación de la variable de control en cada iteración.
- Cuerpo: instrucciones que se repiten.
Se comprueba la condición antes de ejecutar el cuerpo. Puede que no se ejecute ninguna vez.
// Java
int i = 0;
while (i < 5) {
System.out.println("Iteración: " + i);
i++;
}
// Imprime 0, 1, 2, 3, 4
MIENTRAS condicion HACER
instrucciones
FIN MIENTRAS
Se ejecuta el cuerpo al menos una vez, y luego se comprueba la condición.
int i = 0;
do {
System.out.println("Iteración: " + i);
i++;
} while (i < 5);
HACER
instrucciones
MIENTRAS condicion
Diferencia clave (oposición):
whilepuede ejecutarse 0 veces;do-whilese ejecuta al menos 1 vez.
Ideal cuando se conoce el número de iteraciones de antemano.
// Java
for (int i = 0; i < 5; i++) {
System.out.println("i = " + i);
}
// For mejorado (for-each) para colecciones
int[] numeros = {10, 20, 30, 40};
for (int n : numeros) {
System.out.println(n);
}
# Python
for i in range(5): # 0, 1, 2, 3, 4
print(i)
for i in range(2, 10, 2): # 2, 4, 6, 8
print(i)
PARA i DESDE 1 HASTA 10 PASO 1 HACER
instrucciones
FIN PARA
| Instrucción | Acción |
|---|---|
break |
Sale inmediatamente del bucle |
continue |
Salta a la siguiente iteración |
return |
Sale del método/función completo |
for (int i = 0; i < 10; i++) {
if (i == 3) continue; // Salta el 3
if (i == 7) break; // Sale del bucle al llegar a 7
System.out.print(i + " "); // Imprime: 0 1 2 4 5 6
}
La recursividad es una técnica en la que una función se llama a sí misma para resolver un problema, dividiéndolo en subproblemas más pequeños del mismo tipo.
Requisitos para que sea correcta:
1. Caso base: condición que detiene la recursión (sin él → bucle infinito / desbordamiento de pila).
2. Caso recursivo: la función se llama a sí misma con un argumento que se acerca al caso base.
n! = n × (n-1) × (n-2) × ... × 1
0! = 1 (caso base)
// Java - Recursivo
int factorial(int n) {
if (n == 0) return 1; // Caso base
return n * factorial(n - 1); // Caso recursivo
}
// factorial(5) = 5 × 4 × 3 × 2 × 1 = 120
// Java - Iterativo (equivalente)
int factorialIterativo(int n) {
int resultado = 1;
for (int i = 1; i <= n; i++) {
resultado *= i;
}
return resultado;
}
F(0) = 0, F(1) = 1
F(n) = F(n-1) + F(n-2)
int fibonacci(int n) {
if (n <= 1) return n; // Casos base
return fibonacci(n - 1) + fibonacci(n - 2); // Caso recursivo
}
// fibonacci(6) = 0,1,1,2,3,5,8 → 8
factorial(4)
→ 4 * factorial(3)
→ 3 * factorial(2)
→ 2 * factorial(1)
→ 1 * factorial(0)
→ 1 (caso base)
→ 1 * 1 = 1
→ 2 * 1 = 2
→ 3 * 2 = 6
→ 4 * 6 = 24
| Aspecto | Recursión | Iteración |
|---|---|---|
| Legibilidad | Alta (problemas divisibles) | Alta (secuencial) |
| Memoria | Mayor (pila de llamadas) | Menor |
| Riesgo | Stack Overflow | Bucle infinito |
| Rendimiento | Menor (overhead de llamadas) | Mayor |
| Uso ideal | Árboles, grafos, divide y vencerás | Cálculos simples |
Un subprograma (procedimiento o función) es un bloque de código con nombre que realiza una tarea específica y puede ser invocado desde cualquier parte del programa.
Ventajas:
- Reutilización: escribir una vez, usar muchas.
- Modularidad: dividir el problema en partes manejables.
- Abstracción: ocultar detalles de implementación.
- Mantenimiento: cambios localizados.
| Característica | Procedimiento | Función |
|---|---|---|
| Devuelve valor | No | Sí |
| Palabra clave | void / procedure |
function / tipo de retorno |
| Propósito | Realizar una acción | Calcular y devolver un resultado |
// Procedimiento (no devuelve nada)
void mostrarBienvenida(String nombre) {
System.out.println("Bienvenido, " + nombre + "!");
}
// Función (devuelve un valor)
int sumar(int a, int b) {
return a + b;
}
// Uso
mostrarBienvenida("Ana"); // Llama al procedimiento
int resultado = sumar(3, 5); // Llama a la función → resultado = 8
int a, int b).sumar(3, 5)).Se copia el valor. Cambios en la función NO afectan a la variable original.
void duplicar(int x) {
x = x * 2; // Solo modifica la copia local
System.out.println("Dentro: " + x); // 10
}
int num = 5;
duplicar(num);
System.out.println("Fuera: " + num); // Sigue siendo 5
Se pasa la dirección de memoria. Cambios en la función SÍ afectan a la variable original.
// En C, se simula con punteros
void duplicar(int *x) {
*x = *x * 2; // Modifica el valor en la dirección apuntada
}
int num = 5;
duplicar(&num);
printf("%d", num); // num ahora es 10
// En Java: los objetos se pasan por referencia de valor
// (se pasa la referencia, no el objeto completo)
void modificar(int[] arr) {
arr[0] = 99; // Sí modifica el array original
}
Resumen para oposición: En Java, los tipos primitivos se pasan por valor; los objetos y arrays se pasan por referencia (técnicamente, la referencia por valor).
La expresión del argumento se evalúa cada vez que se usa el parámetro dentro de la función. Usado en ALGOL. Poco común hoy.
int global = 100; // Variable global
void ejemplo() {
int local = 50; // Variable local
System.out.println(global); // OK: accede a la global
System.out.println(local); // OK: accede a la local
}
// Aquí NO se puede acceder a 'local'
Cada llamada recursiva crea un nuevo marco de pila (stack frame) con sus propias variables locales.
Pila de llamadas para factorial(3):
┌─────────────────┐
│ factorial(0)=1 │ ← cima (último en entrar)
├─────────────────┤
│ factorial(1)=1 │
├─────────────────┤
│ factorial(2)=2 │
├─────────────────┤
│ factorial(3)=6 │ ← base
└─────────────────┘
Mismo nombre de función, diferente número o tipo de parámetros.
int sumar(int a, int b) { return a + b; }
double sumar(double a, double b) { return a + b; }
int sumar(int a, int b, int c) { return a + b + c; }
sumar(1, 2); // llama a la primera
sumar(1.5, 2.5); // llama a la segunda
sumar(1, 2, 3); // llama a la tercera
Un vector (o array / tabla) es una estructura de datos que almacena un conjunto de elementos del mismo tipo en posiciones de memoria contiguas, accesibles mediante un índice.
// Java
int[] notas = new int[5]; // Vector de 5 enteros (sin inicializar → todos 0)
int[] pares = {2, 4, 6, 8, 10}; // Con inicialización directa
pares[0] = 2; // Primer elemento
pares[4] = 10; // Último elemento
// pares[5] → ArrayIndexOutOfBoundsException (fuera de rango)
// C
int notas[5]; // Declara 5 enteros
int pares[] = {2, 4, 6, 8, 10}; // Con inicialización
notas[0] = 7; // Acceso
# Python (listas dinámicas)
notas = [0] * 5 # Lista de 5 ceros
pares = [2, 4, 6, 8, 10]
print(pares[2]) # 6
int[] v = {5, 3, 8, 1, 9};
// Recorrido con for clásico
for (int i = 0; i < v.length; i++) {
System.out.print(v[i] + " "); // 5 3 8 1 9
}
// Recorrido con for-each
for (int elem : v) {
System.out.print(elem + " ");
}
// Búsqueda lineal: O(n)
int buscarLineal(int[] v, int objetivo) {
for (int i = 0; i < v.length; i++) {
if (v[i] == objetivo) return i; // Devuelve el índice
}
return -1; // No encontrado
}
// Búsqueda binaria (el vector debe estar ORDENADO): O(log n)
int buscarBinaria(int[] v, int objetivo) {
int izq = 0, der = v.length - 1;
while (izq <= der) {
int medio = (izq + der) / 2;
if (v[medio] == objetivo) return medio;
else if (v[medio] < objetivo) izq = medio + 1;
else der = medio - 1;
}
return -1;
}
// Bubble Sort: O(n²)
void burbuja(int[] v) {
int n = v.length;
for (int i = 0; i < n - 1; i++) {
for (int j = 0; j < n - i - 1; j++) {
if (v[j] > v[j + 1]) {
// Intercambio
int temp = v[j];
v[j] = v[j + 1];
v[j + 1] = temp;
}
}
}
}
// Matriz 3×3 en Java
int[][] matriz = {
{1, 2, 3},
{4, 5, 6},
{7, 8, 9}
};
// Acceso: matriz[fila][columna]
System.out.println(matriz[1][2]); // 6 (fila 1, columna 2)
// Recorrido
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
System.out.print(matriz[i][j] + " ");
}
System.out.println();
}
Un registro (struct en C, record en Pascal) es una estructura de datos que agrupa variables de distintos tipos bajo un mismo nombre. Equivale a un objeto simple (sin métodos).
// Definición del tipo registro
struct Alumno {
char nombre[50];
int edad;
float nota;
};
// Uso
struct Alumno a1;
strcpy(a1.nombre, "María García");
a1.edad = 22;
a1.nota = 8.5;
// Acceso a campos con el operador punto (.)
printf("Nombre: %s\n", a1.nombre);
printf("Nota: %.1f\n", a1.nota);
TYPE
TAlumno = RECORD
nombre : STRING[50];
edad : INTEGER;
nota : REAL;
END;
VAR
alumno1 : TAlumno;
BEGIN
alumno1.nombre := 'María';
alumno1.edad := 22;
alumno1.nota := 8.5;
END.
class Alumno {
String nombre;
int edad;
double nota;
}
Alumno a = new Alumno();
a.nombre = "María García";
a.edad = 22;
a.nota = 8.5;
Combinación potente: lista de registros.
struct Alumno clase[30]; // Array de 30 alumnos
// Inicializar el primero
strcpy(clase[0].nombre, "Ana López");
clase[0].edad = 20;
clase[0].nota = 7.5;
// Recorrer y mostrar todos
for (int i = 0; i < 30; i++) {
printf("%s - %d años - %.1f\n",
clase[i].nombre, clase[i].edad, clase[i].nota);
}
| Característica | Vector (Array) | Registro (Struct) |
|---|---|---|
| Tipos de datos | Homogéneo (mismo tipo) | Heterogéneo (distintos tipos) |
| Acceso | Por índice numérico | Por nombre de campo |
| Tamaño | Fijo en declaración | Definido en la estructura |
| Uso típico | Colecciones del mismo tipo | Representar una entidad |
Todo programa tiene al menos tres partes conceptuales:
┌─────────────────────────────┐
│ CABECERA │ Nombre, metadatos, imports
├─────────────────────────────┤
│ DECLARACIONES GLOBALES │ Constantes, tipos, variables globales
├─────────────────────────────┤
│ SUBPROGRAMAS │ Funciones y procedimientos
├─────────────────────────────┤
│ PROGRAMA PRINCIPAL │ Punto de entrada (main)
└─────────────────────────────┘
PROGRAMA nombre_del_programa
CONSTANTES
PI = 3.14159
MAX = 100
TIPOS
TAlumno = REGISTRO
nombre: CADENA
nota: REAL
FIN REGISTRO
VARIABLES
edad: ENTERO
nombre: CADENA
FUNCIÓN calcularArea(radio: REAL): REAL
INICIO
DEVOLVER PI * radio * radio
FIN FUNCIÓN
PROCEDIMIENTO mostrar(texto: CADENA)
INICIO
ESCRIBIR(texto)
FIN PROCEDIMIENTO
INICIO // Programa principal
nombre ← "Ana"
edad ← 25
mostrar("Hola, " + nombre)
ESCRIBIR(calcularArea(5.0))
FIN
/* ====== Cabecera ====== */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/* ====== Constantes ====== */
#define MAX 100
#define PI 3.14159
/* ====== Tipos definidos por el usuario ====== */
typedef struct {
char nombre[50];
int edad;
float nota;
} Alumno;
/* ====== Variables globales ====== */
int contador = 0;
/* ====== Declaración de funciones ====== */
float calcularMedia(float notas[], int n);
void mostrarAlumno(Alumno a);
/* ====== Función principal ====== */
int main() {
// Declaraciones locales
float notas[] = {7.5, 8.0, 6.5, 9.0};
Alumno a1;
// Instrucciones
strcpy(a1.nombre, "Carlos Ruiz");
a1.edad = 21;
a1.nota = calcularMedia(notas, 4);
mostrarAlumno(a1);
return 0; // 0 indica ejecución exitosa
}
/* ====== Implementación de funciones ====== */
float calcularMedia(float notas[], int n) {
float suma = 0;
for (int i = 0; i < n; i++) suma += notas[i];
return suma / n;
}
void mostrarAlumno(Alumno a) {
printf("Nombre: %s\nEdad: %d\nNota: %.2f\n",
a.nombre, a.edad, a.nota);
}
/* ====== Paquete e imports ====== */
package com.ejemplo;
import java.util.Scanner;
/* ====== Clase principal ====== */
public class GestionAlumnos {
/* ====== Constantes de clase ====== */
static final int MAX_ALUMNOS = 30;
/* ====== Atributos de clase ====== */
static int totalAlumnos = 0;
/* ====== Método principal ====== */
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.print("Introduce una nota: ");
double nota = sc.nextDouble();
String calificacion = obtenerCalificacion(nota);
System.out.println("Calificación: " + calificacion);
sc.close();
}
/* ====== Métodos auxiliares ====== */
static String obtenerCalificacion(double nota) {
if (nota >= 9) return "Sobresaliente";
else if (nota >= 7) return "Notable";
else if (nota >= 5) return "Aprobado";
else return "Suspenso";
}
static double calcularMedia(double[] notas) {
double suma = 0;
for (double n : notas) suma += n;
return suma / notas.length;
}
}
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Módulo de gestión de alumnos
"""
# ====== Imports ======
import sys
# ====== Constantes ======
MAX_ALUMNOS = 30
PI = 3.14159
# ====== Funciones ======
def calcular_media(notas: list) -> float:
"""Calcula la media de una lista de notas."""
if not notas:
return 0.0
return sum(notas) / len(notas)
def obtener_calificacion(nota: float) -> str:
"""Devuelve la calificación textual de una nota."""
if nota >= 9:
return "Sobresaliente"
elif nota >= 7:
return "Notable"
elif nota >= 5:
return "Aprobado"
else:
return "Suspenso"
# ====== Programa principal ======
def main():
notas = [7.5, 8.0, 9.5, 6.0, 5.5]
media = calcular_media(notas)
calificacion = obtener_calificacion(media)
print(f"Media: {media:.2f}")
print(f"Calificación: {calificacion}")
if __name__ == "__main__":
main()
1. ESCRITURA → El programador escribe el código fuente (.c, .java, .py)
2. COMPILACIÓN → El compilador traduce a código objeto / bytecode
3. ENLAZADO → El linker une código objeto con bibliotecas → ejecutable
4. CARGA → El SO carga el ejecutable en memoria RAM
5. EJECUCIÓN → La CPU ejecuta las instrucciones
6. FINALIZACIÓN → El programa libera recursos y devuelve el control al SO
┌──────────────────────────────┐ Dirección alta
│ PILA (Stack) │ Variables locales, marcos de función
│ (crece hacia abajo) │
├──────────────────────────────┤
│ │
│ MONTÓN (Heap) │ Memoria dinámica (new, malloc)
│ (crece hacia arriba) │
│ │
├──────────────────────────────┤
│ SEGMENTO DE DATOS (.data) │ Variables globales y estáticas
├──────────────────────────────┤
│ SEGMENTO DE CÓDIGO (.text) │ Instrucciones del programa
└──────────────────────────────┘ Dirección baja
| Tema | Concepto Crítico |
|---|---|
| Lenguajes | Compilador genera ejecutable; intérprete ejecuta línea a línea |
| Tipos | IEEE 754 para flotantes; complemento a 2 para enteros negativos |
| Operadores | Precedencia: ! > * / > + - > comparación > && > \|\| |
| Condicionales | switch sin break produce fall-through |
| Bucles | while puede ejecutarse 0 veces; do-while al menos 1 vez |
| Recursividad | Siempre necesita caso base; usa la pila de llamadas |
| Paso de parámetros | Por valor: no modifica original; por referencia: sí modifica |
| Arrays | Homogéneos, índice desde 0, acceso O(1) |
| Registros | Heterogéneos, acceso por nombre de campo |
| Estructura | Todo programa: cabecera + declaraciones + subprogramas + main |
Guía elaborada para preparación de oposiciones. Temas: Lenguajes de Programación, Tipos de Datos, Operadores, Condicionales, Bucles, Recursividad, Funciones, Vectores, Registros y Estructura de Programas.