🧚 ¡Escucha! Beekeeper Studio es una GUI de base de datos rápida, moderna y de código abierto Descargar
January 13, 2026 Por Matthew Rathbone

Calcular la diferencia entre dos fechas es una de las tareas más comunes en el trabajo con bases de datos. Ya sea que estés rastreando duraciones de proyectos, encontrando facturas vencidas o calculando la antigüedad de clientes, necesitas formas confiables de medir intervalos de tiempo. Ahí es donde SQL DATEDIFF y la aritmética de fechas se vuelven esenciales.

Los cálculos de diferencia de fechas aparecen en todas partes en aplicaciones reales: informes de antigüedad, seguimiento de suscripciones, monitoreo de SLA y un sinfín de escenarios de análisis de negocios. Aunque la función específica varía entre sistemas de bases de datos, el concepto central permanece igual—medir la distancia entre dos puntos en el tiempo.

A lo largo de esta guía, encontrarás ejercicios SQL interactivos que te permiten practicar cálculos de fechas en tu navegador—sin necesidad de configurar una base de datos. Escribe consultas, obtén retroalimentación instantánea y gana confianza con la aritmética de fechas.

¿Qué es DATEDIFF?

DATEDIFF es una función SQL que calcula la diferencia entre dos fechas. La sintaxis exacta varía según el sistema de base de datos, pero el concepto es universal: dadas dos fechas, devuelve qué tan separadas están.

La idea general funciona así:

-- Sintaxis conceptual (varía según la base de datos)
DATEDIFF(unidad, fecha_inicio, fecha_fin)
-- o
DATEDIFF(fecha_fin, fecha_inicio)

Puntos clave sobre los cálculos de diferencia de fechas:

  • Las unidades varían: Algunas bases de datos te permiten especificar días, meses, años, horas, etc.
  • El orden importa: El resultado puede ser positivo o negativo dependiendo de qué fecha viene primero
  • Específico de la base de datos: Cada base de datos tiene su propia sintaxis y funciones

Aritmética de Fechas en Diferentes Bases de Datos

Dado que la sintaxis de DATEDIFF varía significativamente entre bases de datos, aquí está cómo cada sistema principal lo maneja:

SQL Server

-- DATEDIFF(parte_fecha, fecha_inicio, fecha_fin)
SELECT DATEDIFF(day, '2024-01-01', '2024-01-15') as dias_diff;
-- Devuelve: 14

SELECT DATEDIFF(month, '2024-01-15', '2024-06-15') as meses_diff;
-- Devuelve: 5

MySQL

-- DATEDIFF(fecha_fin, fecha_inicio) - devuelve solo días
SELECT DATEDIFF('2024-01-15', '2024-01-01') as dias_diff;
-- Devuelve: 14

-- Para otras unidades, usa TIMESTAMPDIFF
SELECT TIMESTAMPDIFF(MONTH, '2024-01-15', '2024-06-15') as meses_diff;
-- Devuelve: 5

PostgreSQL

-- La resta directa devuelve un intervalo
SELECT '2024-01-15'::date - '2024-01-01'::date as dias_diff;
-- Devuelve: 14

-- O usa AGE() para un desglose detallado
SELECT AGE('2024-06-15', '2024-01-15');
-- Devuelve: 5 mons

SQLite

SQLite no tiene una función DATEDIFF incorporada, pero puedes usar cálculos de día Juliano:

-- Resta días Julianos para la diferencia de fechas
SELECT julianday('2024-01-15') - julianday('2024-01-01') as dias_diff;
-- Devuelve: 14.0

-- Convierte a entero para días completos
SELECT CAST(julianday('2024-01-15') - julianday('2024-01-01') AS INTEGER);
-- Devuelve: 14

Cálculos Básicos de Diferencia de Fechas

Comencemos con el escenario más común: calcular el número de días entre dos fechas.

Días Entre Fechas

Imagina que estás rastreando tiempos de cumplimiento de pedidos. Tienes una fecha de pedido y una fecha de envío, y necesitas saber cuánto tiempo tomó el cumplimiento:

-- SQL Server
SELECT 
  id_pedido,
  fecha_pedido,
  fecha_envio,
  DATEDIFF(day, fecha_pedido, fecha_envio) as dias_cumplimiento
FROM pedidos;

-- MySQL
SELECT 
  id_pedido,
  fecha_pedido,
  fecha_envio,
  DATEDIFF(fecha_envio, fecha_pedido) as dias_cumplimiento
FROM pedidos;

-- SQLite
SELECT 
  id_pedido,
  fecha_pedido,
  fecha_envio,
  CAST(julianday(fecha_envio) - julianday(fecha_pedido) AS INTEGER) as dias_cumplimiento
FROM pedidos;

Inténtalo tú mismo:

[[ expanded ? '▼' : '▶' ]]

[[ testData.title ]]

Consulta la tabla projects para obtener project_name, start_date, end_date, y calcula duration_days como el número de días entre las fechas de inicio y fin.

Ejemplo Interactivo ✓ Completado
Columnas esperadas: [[ col ]]
ℹ️ Este ejercicio reinicia la base de datos en cada ejecución. Escribe tu solución completa en un solo envío.
[[ i18n.correct ]] [[ validationResult ? i18n.all_checks_passed : i18n.query_success ]]
[[ detail.message ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.not_quite_right ]] [[ patternError ]] [[ validationResult.error ]] [[ i18n.results_dont_match ]]
[[ detail.passed ? '✓' : '✗' ]] [[ detail.message ]]
[[ i18n.your_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.expected_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.sql_error ]]
[[ error ]]
💡 [[ i18n.hint_label ]] [[ testData.hint ]]
📊 [[ i18n.expected_result_label ]]
[[ col ]]
[[ formatCell(cell) ]]
✨ [[ i18n.solution_label ]]
[[ testData.solution ]]
Tablas Disponibles
[[ table.name ]]
[[ col ]]
[[ formatCell(cell) ]]

Encontrar Registros Vencidos

Un requisito comercial común es encontrar registros que han pasado su fecha límite y calcular cuánto tiempo llevan vencidos.

-- Encontrar facturas vencidas a la fecha de hoy
-- SQL Server
SELECT 
  id_factura,
  fecha_vencimiento,
  DATEDIFF(day, fecha_vencimiento, GETDATE()) as dias_vencidos
FROM facturas
WHERE fecha_vencimiento < GETDATE();

-- MySQL
SELECT 
  id_factura,
  fecha_vencimiento,
  DATEDIFF(CURDATE(), fecha_vencimiento) as dias_vencidos
FROM facturas
WHERE fecha_vencimiento < CURDATE();

-- SQLite
SELECT 
  id_factura,
  fecha_vencimiento,
  CAST(julianday('now') - julianday(fecha_vencimiento) AS INTEGER) as dias_vencidos
FROM facturas
WHERE fecha_vencimiento < date('now');

Inténtalo tú mismo:

[[ expanded ? '▼' : '▶' ]]

[[ testData.title ]]

Consulta la tabla tasks para encontrar todas las tareas vencidas (donde due_date es anterior a ‘2024-03-15’). Devuelve task_name, due_date, y calcula days_overdue mostrando cuántos días han pasado desde la fecha límite. Ordena por días vencidos descendente.

Ejemplo Interactivo ✓ Completado
Columnas esperadas: [[ col ]]
ℹ️ Este ejercicio reinicia la base de datos en cada ejecución. Escribe tu solución completa en un solo envío.
[[ i18n.correct ]] [[ validationResult ? i18n.all_checks_passed : i18n.query_success ]]
[[ detail.message ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.not_quite_right ]] [[ patternError ]] [[ validationResult.error ]] [[ i18n.results_dont_match ]]
[[ detail.passed ? '✓' : '✗' ]] [[ detail.message ]]
[[ i18n.your_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.expected_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.sql_error ]]
[[ error ]]
💡 [[ i18n.hint_label ]] [[ testData.hint ]]
📊 [[ i18n.expected_result_label ]]
[[ col ]]
[[ formatCell(cell) ]]
✨ [[ i18n.solution_label ]]
[[ testData.solution ]]
Tablas Disponibles
[[ table.name ]]
[[ col ]]
[[ formatCell(cell) ]]

Calcular Antigüedad en Diferentes Unidades

A veces necesitas la diferencia en meses, años u otras unidades en lugar de solo días.

Meses Entre Fechas

-- SQL Server - meses precisos
SELECT DATEDIFF(month, '2024-01-15', '2024-06-20') as meses_diff;
-- Devuelve: 5

-- MySQL
SELECT TIMESTAMPDIFF(MONTH, '2024-01-15', '2024-06-20') as meses_diff;
-- Devuelve: 5

-- PostgreSQL
SELECT EXTRACT(YEAR FROM AGE('2024-06-20', '2024-01-15')) * 12 +
       EXTRACT(MONTH FROM AGE('2024-06-20', '2024-01-15')) as meses_diff;

-- SQLite (aproximado - dividiendo días entre 30)
SELECT CAST((julianday('2024-06-20') - julianday('2024-01-15')) / 30 AS INTEGER);
-- Devuelve: 5

Años Entre Fechas

-- SQL Server
SELECT DATEDIFF(year, '2020-03-15', '2024-06-20') as anios_diff;

-- MySQL
SELECT TIMESTAMPDIFF(YEAR, '2020-03-15', '2024-06-20') as anios_diff;

-- PostgreSQL
SELECT EXTRACT(YEAR FROM AGE('2024-06-20', '2020-03-15')) as anios_diff;

-- SQLite (aproximado)
SELECT CAST((julianday('2024-06-20') - julianday('2020-03-15')) / 365 AS INTEGER);

Inténtalo tú mismo:

[[ expanded ? '▼' : '▶' ]]

[[ testData.title ]]

Consulta la tabla accounts para obtener account_name, created_date, y calcula age_months mostrando cuántos meses completos tiene cada cuenta (a fecha de ‘2024-06-01’). Ordena por edad en meses descendente.

Ejemplo Interactivo ✓ Completado
Columnas esperadas: [[ col ]]
ℹ️ Este ejercicio reinicia la base de datos en cada ejecución. Escribe tu solución completa en un solo envío.
[[ i18n.correct ]] [[ validationResult ? i18n.all_checks_passed : i18n.query_success ]]
[[ detail.message ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.not_quite_right ]] [[ patternError ]] [[ validationResult.error ]] [[ i18n.results_dont_match ]]
[[ detail.passed ? '✓' : '✗' ]] [[ detail.message ]]
[[ i18n.your_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.expected_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.sql_error ]]
[[ error ]]
💡 [[ i18n.hint_label ]] [[ testData.hint ]]
📊 [[ i18n.expected_result_label ]]
[[ col ]]
[[ formatCell(cell) ]]
✨ [[ i18n.solution_label ]]
[[ testData.solution ]]
Tablas Disponibles
[[ table.name ]]
[[ col ]]
[[ formatCell(cell) ]]

Trabajando con Rangos de Fechas

Encontrar registros dentro de un cierto número de días desde una fecha objetivo es otro patrón común.

-- Encontrar todos los eventos dentro de 7 días de una fecha objetivo
-- SQL Server
SELECT nombre_evento, fecha_evento
FROM eventos
WHERE ABS(DATEDIFF(day, fecha_evento, '2024-04-15')) <= 7;

-- MySQL
SELECT nombre_evento, fecha_evento
FROM eventos
WHERE ABS(DATEDIFF(fecha_evento, '2024-04-15')) <= 7;

-- SQLite
SELECT nombre_evento, fecha_evento
FROM eventos
WHERE ABS(julianday(fecha_evento) - julianday('2024-04-15')) <= 7;

Inténtalo tú mismo:

[[ expanded ? '▼' : '▶' ]]

[[ testData.title ]]

Consulta la tabla events para encontrar todos los eventos que ocurrieron dentro de 7 días antes o después de ‘2024-04-15’. Devuelve event_name, event_date, y days_from_target mostrando la diferencia (negativo para antes, positivo para después). Ordena por event_date.

Ejemplo Interactivo ✓ Completado
Columnas esperadas: [[ col ]]
ℹ️ Este ejercicio reinicia la base de datos en cada ejecución. Escribe tu solución completa en un solo envío.
[[ i18n.correct ]] [[ validationResult ? i18n.all_checks_passed : i18n.query_success ]]
[[ detail.message ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.not_quite_right ]] [[ patternError ]] [[ validationResult.error ]] [[ i18n.results_dont_match ]]
[[ detail.passed ? '✓' : '✗' ]] [[ detail.message ]]
[[ i18n.your_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.expected_results ]]
[[ col ]]
[[ formatCell(cell) ]]
[[ i18n.sql_error ]]
[[ error ]]
💡 [[ i18n.hint_label ]] [[ testData.hint ]]
📊 [[ i18n.expected_result_label ]]
[[ col ]]
[[ formatCell(cell) ]]
✨ [[ i18n.solution_label ]]
[[ testData.solution ]]
Tablas Disponibles
[[ table.name ]]
[[ col ]]
[[ formatCell(cell) ]]

Ejemplos Prácticos

Análisis de Antigüedad de Clientes

Calcula cuánto tiempo llevan los clientes contigo:

-- Ejemplo SQLite
SELECT 
  nombre_cliente,
  fecha_registro,
  CAST((julianday('now') - julianday(fecha_registro)) / 365 AS INTEGER) as anios_con_nosotros,
  CASE 
    WHEN julianday('now') - julianday(fecha_registro) < 365 THEN 'Nuevo'
    WHEN julianday('now') - julianday(fecha_registro) < 730 THEN 'Establecido'
    ELSE 'Leal'
  END as nivel_cliente
FROM clientes;

Monitoreo de SLA

Rastrea tiempos de respuesta contra acuerdos de nivel de servicio:

-- Ejemplo SQLite
SELECT 
  id_ticket,
  creado_en,
  resuelto_en,
  CAST(julianday(resuelto_en) - julianday(creado_en) AS INTEGER) as dias_resolucion,
  CASE 
    WHEN julianday(resuelto_en) - julianday(creado_en) <= 3 THEN 'Dentro de SLA'
    ELSE 'Incumplimiento SLA'
  END as estado_sla
FROM tickets_soporte;

Renovaciones de Suscripción

Encuentra suscripciones que expiran dentro de un cierto período:

-- Ejemplo SQLite - suscripciones que expiran en los próximos 30 días
SELECT 
  nombre_cliente,
  fin_suscripcion,
  CAST(julianday(fin_suscripcion) - julianday('now') AS INTEGER) as dias_restantes
FROM suscripciones
WHERE julianday(fin_suscripcion) - julianday('now') BETWEEN 0 AND 30
ORDER BY dias_restantes;

Errores Comunes

Valores de Fecha NULL

Los cálculos de diferencia de fechas devuelven NULL si alguna fecha es NULL:

-- Esto devuelve NULL, no un error
SELECT julianday(NULL) - julianday('2024-01-01');

-- Maneja NULLs explícitamente
SELECT COALESCE(
  CAST(julianday(fecha_fin) - julianday(fecha_inicio) AS INTEGER),
  0
) as dias_duracion
FROM proyectos;

Problemas de Formato de Fecha

Asegúrate de que tus fechas estén en el formato correcto:

-- SQLite espera formato ISO: YYYY-MM-DD
-- Esto funciona:
SELECT julianday('2024-01-15');

-- Esto podría no funcionar como se espera:
SELECT julianday('15-01-2024');
SELECT julianday('01/15/2024');

Sorpresas con el Componente de Hora

Cuando las fechas incluyen componentes de hora, los resultados podrían no coincidir con las expectativas:

-- Técnicamente están a 0 días de distancia (mismo día calendario)
-- pero la diferencia incluye el componente de hora
SELECT julianday('2024-01-15 23:59:59') - julianday('2024-01-15 00:00:00');
-- Devuelve: ~0.999988

-- Elimina la hora para cálculos solo de días
SELECT julianday(date('2024-01-15 23:59:59')) - julianday(date('2024-01-15 00:00:00'));
-- Devuelve: 0

Consejos de Rendimiento

Indexa Columnas de Fecha

Si filtras o calculas frecuentemente basándote en fechas, indexa esas columnas:

CREATE INDEX idx_pedidos_fecha_pedido ON pedidos(fecha_pedido);
CREATE INDEX idx_pedidos_fecha_envio ON pedidos(fecha_envio);

Evita Funciones en Cláusulas WHERE

Las funciones en columnas previenen el uso de índices:

-- Mal: Función en columna previene uso de índice
SELECT * FROM pedidos
WHERE julianday(fecha_pedido) > julianday('2024-01-01');

-- Mejor: Compara directamente
SELECT * FROM pedidos
WHERE fecha_pedido > '2024-01-01';

Pre-calcula para Reportes

Para cálculos de fecha complejos en reportes, considera almacenar valores calculados:

-- Añade una columna calculada o tabla separada para valores frecuentemente necesarios
ALTER TABLE pedidos ADD COLUMN dias_cumplimiento INTEGER;

UPDATE pedidos 
SET dias_cumplimiento = CAST(julianday(fecha_envio) - julianday(fecha_pedido) AS INTEGER)
WHERE fecha_envio IS NOT NULL;

Trabajando con Cálculos de Fecha en Beekeeper Studio

Cuando trabajas con cálculos de fecha complejos, un editor SQL potente marca la diferencia. Beekeeper Studio proporciona excelente soporte para escribir y probar consultas de fechas.

Características que ayudan con cálculos de fecha:

  • Autocompletado de consultas: Sugiere funciones de fecha mientras escribes
  • Formato de resultados: Muestra fechas en formatos legibles
  • Soporte multi-base de datos: Trabaja con funciones de fecha en PostgreSQL, MySQL, SQLite, SQL Server y más
  • Historial de consultas: Guarda y reutiliza tus patrones de cálculo de fechas

La versión gratuita incluye todo lo que necesitas para dominar los cálculos de fecha SQL, haciéndola perfecta tanto para aprender como para trabajo de producción con bases de datos.

Puntos Clave

Calcular diferencias de fecha es fundamental para el trabajo con bases de datos. Esto es lo que debes recordar:

  • La sintaxis de DATEDIFF varía según la base de datos - aprende el enfoque de tu sistema específico
  • SQLite usa julianday() para aritmética de fechas ya que carece de un DATEDIFF nativo
  • El orden importa - sabe qué fecha viene primero para obtener resultados positivos o negativos
  • Maneja valores NULL - los cálculos de fecha con NULL devuelven NULL
  • Cuida los formatos de fecha - usa formato ISO (YYYY-MM-DD) para consistencia
  • Considera los componentes de hora - usa la función date() cuando necesites cálculos solo de días
  • Indexa columnas de fecha - mejora el rendimiento para consultas basadas en fechas
  • Prueba casos límite - años bisiestos, límites de mes y problemas de zona horaria pueden sorprenderte

Al dominar los cálculos de diferencia de fecha, estarás equipado para manejar informes de antigüedad, rastrear duraciones, monitorear fechas límite y construir aplicaciones conscientes del tiempo. Ya sea calculando la antigüedad de clientes o encontrando tareas vencidas, estas técnicas son esenciales para el trabajo real con bases de datos.

¿Listo para practicar más? Prueba los ejemplos interactivos de arriba, o explora más tutoriales SQL para continuar desarrollando tu experiencia en bases de datos.

Beekeeper Studio Es Una GUI de Base de Datos Gratuita y de Código Abierto

La mejor herramienta de consultas y editor SQL que he usado. Proporciona todo lo que necesito para gestionar mi base de datos. - ⭐⭐⭐⭐⭐ Mit

Beekeeper Studio es rápido, intuitivo y fácil de usar. Beekeeper soporta muchas bases de datos y funciona muy bien en Windows, Mac y Linux.

La versión de Linux de Beekeeper tiene todas las funciones, sin recortes ni compromisos de características.

Lo Que Dicen Los Usuarios Sobre Beekeeper Studio

★★★★★
"Beekeeper Studio reemplazó por completo mi antiguo flujo de trabajo con SQL. Es rápido, intuitivo y hace que trabajar con bases de datos sea agradable de nuevo."
— Alex K., Desarrollador de Bases de Datos
★★★★★
"He probado muchas GUIs de bases de datos, pero Beekeeper logra el equilibrio perfecto entre características y simplicidad. Simplemente funciona."
— Sarah M., Ingeniera Full Stack

¿Listo para Mejorar tu Flujo de Trabajo con SQL?

download Descargar Gratis