No tienes acceso a esta clase

¡Continúa aprendiendo! Únete y comienza a potenciar tu carrera

No se trata de lo que quieres comprar, sino de quién quieres ser. Invierte en tu educación con el precio especial

Antes: $249

Currency
$209

Paga en 4 cuotas sin intereses

Paga en 4 cuotas sin intereses
Suscríbete

Termina en:

12 Días
14 Hrs
26 Min
13 Seg
Curso Práctico de SQL

Curso Práctico de SQL

Israel Vázquez Morales

Israel Vázquez Morales

Selectores de rango

16/29
Recursos

Aportes 157

Preguntas 16

Ordenar por:

¿Quieres ver más aportes, preguntas y respuestas de la comunidad?

Solucion del reto

SELECT INT4RANGE(MIN(tutor_id), MAX(tutor_id)) * INT4RANGE(MIN(carrera_id), MAX(carrera_id))
    FROM platzi.alumnos;

Como cuando crees que dominas Postgres y aparece esto. 😮

En SQL Server

-- CREAR UN RANGO DE VALORES [9; 11]
SELECT TOP 11
	9 + ROW_NUMBER() OVER(PARTITION BY 1 ORDER BY A.name) AS 'Range'
FROM syscolumns A, syscolumns B


-- UNION DE 2 RANGOS
(
	SELECT TOP 9 -- [11; 19]
		10 + ROW_NUMBER() OVER(PARTITION BY 1 ORDER BY A.name) AS 'Range'
	FROM syscolumns A, syscolumns B
)
UNION
(
	SELECT TOP 11 -- [15; 25]
	14 + ROW_NUMBER() OVER(PARTITION BY 1 ORDER BY A.name) AS 'Range'
    FROM syscolumns A, syscolumns B
)

-- INTERSECCION DE 2 RANGOS
(
	SELECT TOP 9 -- [11; 19]
		10 + ROW_NUMBER() OVER(PARTITION BY 1 ORDER BY A.name) AS 'Range'
	FROM syscolumns A, syscolumns B
)
INTERSECT
(
	SELECT TOP 11 -- [15; 25]
	14 + ROW_NUMBER() OVER(PARTITION BY 1 ORDER BY A.name) AS 'Range'
    FROM syscolumns A, syscolumns B
)


-- METODO 3
-- RANGO CON UNA SUBCONSULTA
USE [platzi]
SELECT *
FROM platzi.alumnos
WHERE tutor_id IN
(
	SELECT TOP 11
	9 + ROW_NUMBER() OVER(PARTITION BY 1 ORDER BY A.name) AS 'Range'
	FROM syscolumns A, syscolumns B
)
GO 


/*
INTERSECCION ENTRE CARRERA_ID Y TUTOR_ID
*/

SELECT carrera_id AS interseccion
FROM 
(
	(
		SELECT DISTINCT carrera_id
		FROM platzi.alumnos
	)
	INTERSECT
	(
		SELECT DISTINCT tutor_id
		FROM platzi.alumnos
	)
) AS interseccion_ids


Reto:

<code> 
SELECT *
FROM platzi.alumnos
WHERE tutor_id = carrera_id;

Mi respuesta :

‘=>’ Significa ‘devuelve’ en este apunte

‘&&’ si se solapan estos dos rangos

(11.1,22.2) && (20.0,30.0) => TRUE
(11.1,19.9) && (20.0,30.0) => FALSE

* Para seleccionar los elementos de la interseccion entre los dos rangos. SI no hay, marca error

SELECT int4ramge(10,20) * int4range(15,25) =>[15,20)

@> si el rango se encuentra en el grupo

SELECT *
FROM platzi.alumnos
WHERE int4range(10,20) @> tutor_id

SACAR EL RANGO QUE HAY ENTRE TUTOR_ID Y CARRERA_ID

SELECT int4range(min(tutor_id), max(tutor_id)) * int4range(min(carrera_id), max(carrera_id))
FROM platzi.alumnos;

SACAR LOS DATOS QUE PERTENECEN AL RANGO ENTRE TUTOR_ID Y CARRERA_ID

SELECT *
FROM platzi.alumnos
WHERE(
SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id),MAX(carrera_id))
FROM platzi.alumnos
) @> tutor_id
AND
(
SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id),MAX(carrera_id))
FROM platzi.alumnos
) @> carrera_id;

Selectores de rango
Son especialmente útiles para utilizar en el WHERE statement.

SELECT int4range(1,20) @> 3;

Esta consulta trae un entero pequeño y pregunta si el rango contiene al numero 3

SELECT numrange(11,20) && numrange(20.0, 30.0);

Esta consulta trae un resultado booleano, ya que los && consultan entre los dos rangos de números de alta precisión si existen valores solapados entre ambos

SELECT LOWER int8range(15,25);

Simplemente trae el menor número del rango. Funciona igual con UPPER

SELECT int4range(10,20) * int4range(15,25);

Esta consulta trae el rango numérico que comparten ambos rangos

SELECT ISEMPTY(numrange(1,5));

Booleano que detecta si el rango esta vacío

Mi solución

SELECT 
	numrange(min_carrera, max_carrera) * numrange(min_tutor, max_tutor)
FROM (
	SELECT 
		MIN(carrera_id) as min_carrera,
		MAX(carrera_id) as max_carrera,
		MIN(tutor_id) as min_tutor,
		MAX(tutor_id) as max_tutor
	FROM alumnos
) AS rangos
SELECT *
FROM platzi.alumnos
WHERE int4range(10,20) @> tutor_id 
	AND int4range(10,20) @> carrera_id```

RESPUESTA DEL RETO en MySQL

SELECT a.tutor_id,b.carrera_id
FROM alumnos as a
inner JOIN alumnos as b
ON a.tutor_id = b.carrera_id
group by a.tutor_id
order by a.tutor_id

Hola, entendí que la tarea era traer todos los campos en común, así que este fue mi Query:

NOTA: Antes de realizar esto, verificar los rangos de cada una de las columnas, ya que pueden caer en el rango más amplio (en este caso el de “carrera_id” que es de 1 a 50) y traer lo que este contenga respecto al rango a comparar, en el caso de “tutor_id” que es de 1 a 30, entonces nos seguiría trayendo todos los datos de la tabla sin más.

<SELECT *
FROM PLATZI.ALUMNOS
WHERE INT4RANGE((SELECT MIN(TUTOR_ID) FROM PLATZI.ALUMNOS), 
				(SELECT MAX(TUTOR_ID) FROM PLATZI.ALUMNOS)) 
@> CARRERA_ID;

Mi solución al Reto de la clase.

En este codigo se seleccionan todas las filas que contengan id en común entre carrera y tutor.

SELECT *
FROM platzi.alumnos
WHERE int4range((SELECT MIN(tutor_id) FROM platzi.alumnos), (SELECT MAX(tutor_id) FROM platzi.alumnos)) @> carrera_id;

Solución al reto de la clase anterior

WITH cte AS (
	SELECT id,
	ROW_NUMBER() OVER (
		PARTITION BY
			nombre,
			apellido,
			email,
			colegiatura,
			fecha_incorporacion,
			carrera_id,
			tutor_id
		ORDER BY id ASC
	) AS row
	FROM platzi.alumnos
)
DELETE FROM platzi.alumnos
USING cte
WHERE platzi.alumnos.id = cte.id
AND cte.row > 1;
SELECT ISEMPTY (numrange(1,5)) --FALSE
SELECT ISEMPTY (numrange(1,1)) --TRUE

LOWER= nos devuleve el valor mas bajo de un rango

Use este query y se me borro toda la base de datos, como hago para restaurarla al punto anterior al query.


DELETE FROM platzi.alumnos 
WHERE id IN 
	(SELECT id FROM(
		SELECT id FROM (
			SELECT ROW_NUMBER() OVER( PARTITION BY
				nombre, apellido,
				email, colegiatura,
				fecha_incorporacion, carrera_id,
				tutor_id ORDER BY id ASC) AS row
		FROM platzi.alumnos) AS duplicados 
		WHERE duplicados.row >1) AS duplicados_id);```

Listo!

SELECT 

int4range(
(SELECT MIN (Carrera_id)), (SELECT MAX (Carrera_id))) 
* 
int4range(
(SELECT MIN (tutor_id)), (SELECT MAX (tutor_id)))

FROM platzi.alumnos;
SELECT int4range((SELECT min(carrera_id) FROM platzi.alumnos),
				 (SELECT max(carrera_id) FROM platzi.alumnos)) *
	int4range((SELECT min(tutor_id) FROM platzi.alumnos),
			  (SELECT max(tutor_id) FROM platzi.alumnos));
Realice esta solución al reto: ```js SELECT int4range( MIN(tutor_id),MAX(tutor_id) ) * int4range( MIN(carrera_id),MAX(carrera_id)) FROM platzi.alumnos ```
Lo que se busca en este reto es identificar los números que aparecen tanto en la columna `tutor\_id` como en la columna `carrera\_id` de la tabla `platzi.alumnos`. Es decir, queremos ver qué números son comunes en ambas columnas. \### Ejemplo Más Sencillo Imagina que tienes dos listas de números: * Lista de "tutor\_id": 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 15, 20, 25 * Lista de "carrera\_id": 5, 6, 7, 10, 11, 12, 15, 20, 30, 40 \*\*¿Qué buscamos?\*\* Queremos encontrar los números que están en ambas listas. \*\*Números comunes:\*\* \- En este caso, los números que están en ambas listas son: \*\*5, 6, 7, 10, 15, 20\*\*. \### Resumiendo Entonces, el reto consiste en: 1\. \*\*Tomar todos los números de "tutor\_id" (por ejemplo, 1 a 25). 2\. \*\*Tomar todos los números de "carrera\_id" (por ejemplo, 5 a 40). 3\. \*\*Ver cuáles de esos números se repiten\*\* en ambas listas. A continuación, se enseña dos formas de verlo: ```js ---ENCONTRAR LOS VALORES QUE COINCIDEN ENTRE LAS DOS COLUMNAS DE TUTOR Y CARRERA--- SELECT INT4RANGE(MIN(tutor_id), MAX(tutor_id)) * INT4RANGE(MIN(carrera_id), MAX(carrera_id)) FROM platzi.alumnos; ---ENCONTRAR LOS VALORES QUE COINCIDEN ENTRE LAS DOS COLUMNAS DE TUTOR Y CARRERA/VALOR A VALOR--- SELECT tutor_id AS Interseccion FROM platzi.alumnos INTERSECT SELECT carrera_id FROM platzi.alumnos ORDER BY Interseccion; ```
mi solución un poco distinta select tutor\_id, carrera\_id from platzi.alumnos where tutor\_id between 1 and 100 and tutor\_id = carrera\_id
```js -- Filtrar registros con intersección de rango del carrera_id y tutor_id que estén entre 10 y 13 -- SELECT * FROM platzi.alumnos WHERE int4range(10, 13) @> tutor_id AND int4range(10, 13) @> carrera_id; ```
```js -- Metodo 1 SELECT * FROM alumnos WHERE int4range(10,20) @> tutor_id AND int4range(0,10) @> carrera_id -- Metodo 2 SELECT * FROM alumnos WHERE tutor_id BETWEEN 10 AND 20 AND carrera_id BETWEEN 0 AND 10; -- Metodo 3 WITH alumnosCTE AS ( SELECT * FROM alumnos ), rangeCTE AS ( SELECT int4range(MIN(alumnosCTE.carrera_id),MAX(alumnosCTE.carrera_id)) * int4range(MIN(alumnosCTE.tutor_id),MAX(alumnosCTE.tutor_id)) AS rangeTutorCarrera FROM alumnosCTE ) SELECT * FROM alumnosCTE WHERE tutor_id <@ (SELECT rangeTutorCarrera FROM rangeCTE) AND carrera_id <@ (SELECT rangeTutorCarrera FROM rangeCTE) -- Metodo 4 WITH rangeCTE AS ( SELECT int4range(MIN(carrera_id), MAX(carrera_id)) * int4range(MIN(tutor_id), MAX(tutor_id)) AS rangeTutorCarrera FROM alumnos ) SELECT * FROM alumnos WHERE tutor_id <@ (SELECT rangeTutorCarrera FROM rangeCTE) AND carrera_id <@ (SELECT rangeTutorCarrera FROM rangeCTE); ```
![](https://static.platzi.com/media/user_upload/InterseccionSQL-f85976cf-9429-4fab-96c0-ee6708bc3e94.jpg)
Verificando Limites de valores de ambos campos: ![](https://static.platzi.com/media/user_upload/image-5d9de975-bfdb-4156-a3cf-d36b2083c4a0.jpg) Obtenemos el rango comun: ![](https://static.platzi.com/media/user_upload/image-15924559-c8f8-4163-92a3-d919afdab5b4.jpg)
SELECT ( (SELECT int8range(MIN(tutor\_id),MAX(tutor\_id)) FROM platzi.alumnos) \* (SELECT int8range(MIN(carrera\_id),MAX(carrera\_id)) FROM platzi.alumnos) );
Comparto una cosa que quise hacer, porque no habia entendido bien el ejercicio, esta seria la solicion entre la interseccion de los ids de la tabla de alumnos y la tabla de carreras, de pronto a alguien le sirve. Me mate un rato la cabeza sacandolo, y al final me di cuenta que el ejercicio era otro y mas simple:```js SELECT (SELECT int8range(low_alum_id,high_alum_id) FROM (SELECT MIN(id) AS low_alum_id, MAX(id) AS high_alum_id FROM platzi.alumnos) AS alum) * (SELECT int8range(low_carr_id,high_carr_id) FROM (SELECT MIN(id) AS low_carr_id, MAX(id) AS high_carr_id FROM platzi.carreras) AS carr); ```SELECT (SELECT int8range(low\_alum\_id,high\_alum\_id) FROM (SELECT MIN(id) AS low\_alum\_id, MAX(id) AS high\_alum\_id FROM platzi.alumnos) AS alum) \* (SELECT int8range(low\_carr\_id,high\_carr\_id) FROM (SELECT MIN(id) AS low\_carr\_id, MAX(id) AS high\_carr\_id FROM platzi.carreras) AS carr);
Comparto una cosa que quise hacer, porque no habia entendido bien el ejercicio, esta seria la solicion entre la interseccion de los ids de la tabla de alumnos y la tabla de carreras, de pronto a alguien le sirve. Me mate un rato la cabeza sacandolo, y al final me di cuenta que el ejercicio era otro y mas simple: ```js SELECT (SELECT int8range(low_alum_id,high_alum_id) FROM (SELECT MIN(id) AS low_alum_id, MAX(id) AS high_alum_id FROM platzi.alumnos) AS alum) * (SELECT int8range(low_carr_id,high_carr_id) FROM (SELECT MIN(id) AS low_carr_id, MAX(id) AS high_carr_id FROM platzi.carreras) AS carr); ```SELECT (SELECT int8range(low\_alum\_id,high\_alum\_id) FROM (SELECT MIN(id) AS low\_alum\_id, MAX(id) AS high\_alum\_id FROM platzi.alumnos) AS alum) \* (SELECT int8range(low\_carr\_id,high\_carr\_id) FROM (SELECT MIN(id) AS low\_carr\_id, MAX(id) AS high\_carr\_id FROM platzi.carreras) AS carr);
Mi respuesta es muy diferente a las que veo igual la comparto: ```js SELECT (SELECT int8range(low_alum_id,high_alum_id) FROM (SELECT MIN(id) AS low_alum_id, MAX(id) AS high_alum_id FROM platzi.alumnos) AS alum) * (SELECT int8range(low_carr_id,high_carr_id) FROM (SELECT MIN(id) AS low_carr_id, MAX(id) AS high_carr_id FROM platzi.carreras) AS carr); ```SELECT (SELECT int8range(low\_alum\_id,high\_alum\_id) FROM (SELECT MIN(id) AS low\_alum\_id, MAX(id) AS high\_alum\_id FROM platzi.alumnos) AS alum) \* (SELECT int8range(low\_carr\_id,high\_carr\_id) FROM (SELECT MIN(id) AS low\_carr\_id, MAX(id) AS high\_carr\_id FROM platzi.carreras) AS carr);
📝 Dejo una posible solución al reto ```js SELECT * FROM platzi.alumnos WHERE carrera_id <@ ( SELECT int4range(MIN(carrera_id), MAX(carrera_id)) * int4range(MIN(tutor_id), MAX(tutor_id)) FROM platzi.alumnos ) AND tutor_id <@ ( SELECT int4range(MIN(carrera_id), MAX(carrera_id)) * int4range(MIN(tutor_id), MAX(tutor_id)) FROM platzi.alumnos ) ``` 🤔 No estoy muy segura si esa solución puede ser viable o no al utilizar dos subqueries dentro del `WHERE`, pero me pareció interesante como práctica.
Aqui mi reto: ![](https://static.platzi.com/media/user_upload/Screenshot%202024-04-19%2012.28.50-834d28f6-694c-4dfc-9807-172eaba42492.jpg)
RESPUESTA DEL RETO: ![](https://static.platzi.com/media/user_upload/image-805199a4-a2d1-48cd-8dc6-e8fae5126638.jpg)
**Reto 6** Eliminar duplicados con **SQL Server** Aquí van un par de modos que he descubierto de eliminación de duplicados con SQL Server: ```js DELETE FROM platzi.alumnos WHERE id IN ( SELECT id FROM ( SELECT id, ROW_NUMBER() OVER ( PARTITION BY nombre, apellido, email, colegiatura, fecha_incorporacion, carrera_id, tutor_id ORDER BY id ASC ) AS conteo FROM platzi.alumnos ) AS duplicados WHERE duplicados.conteo > 1); ```- Segunda manera: ```js WITH Duplicados AS ( SELECT *, ROW_NUMBER() OVER ( PARTITION BY nombre, apellido, email, colegiatura, fecha_incorporacion, carrera_id, tutor_id ORDER BY id ASC ) AS conteo FROM platzi.alumnos ) DELETE FROM platzi.alumnos WHERE id IN (SELECT id FROM Duplicados WHERE conteo > 1); ```

Esta es mi solución

Si bien en este caso específico no es necesario aclarar que tutor_id pertenezca también al rango, para asegurarlo añadí esa condición.

SELECT *
FROM platzi.alumnos
WHERE (
	SELECT
	int4range(
		MIN(tutor_id),
		MAX(tutor_id)
	) * 
	int4range(
		MIN(carrera_id),
		MAX(carrera_id)
	) FROM platzi.alumnos) @> carrera_id
	AND
	(
	SELECT
	int4range(
		MIN(tutor_id),
		MAX(tutor_id)
	) * 
	int4range(
		MIN(carrera_id),
		MAX(carrera_id)
	) FROM platzi.alumnos) @> tutor_id;
Si es extraer los valores en común sería este: ```js SELECT * FROM platzi.alumnos WHERE tutor_id = carrera_id; ``` Ahora si es traer los valores que hayan dentro del rango en común sería este: ```js SELECT * FROM platzi.alumnos WHERE (SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id), MAX(carrera_id)) FROM platzi.alumnos ) @> tutor_id AND (SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id),MAX(carrera_id)) FROM platzi.alumnos ) @> carrera_id; ```

Cuando hablamos de “selectores de rango” en el contexto de bases de datos, generalmente nos referimos a la capacidad de seleccionar registros que se encuentran dentro de un rango específico en función de los valores de una columna.

DELETE FROM platzi.alumnos
WHERE id = 1001 AND tutor_id = 2;

Este query eliminará la fila de la tabla alumnos donde el id es 1001 y el tutor_id es 2.

Antes de ejecutar una operación DELETE, es recomendable hacer una copia de seguridad o asegurarte de que estás eliminando los reg
istros correctos, ya que la operación es irreversible.

```js /**challenge**/ DELETE --SELECT*FROM FROM PLATZI.ALUMNOS WHERE ID=( SELECT ID FROM ( SELECT ROW_NUMBER() OVER(PARTITION BY nombre,apellido,email,colegiatura,fecha_incorporacion,carrera_id,tutor_id ORDER BY id) row_id ,* FROM PLATZI.alumnos ORDER BY ID )STUDENT_ROW WHERE ROW_ID>1 ) ```/\*\*challenge\*\*/ DELETE --SELECT\*FROM FROM PLATZI.ALUMNOS WHERE ID=( SELECT ID FROM ( SELECT ROW\_NUMBER() OVER(PARTITION BY nombre,apellido,email,colegiatura,fecha\_incorporacion,carrera\_id,tutor\_id ORDER BY id) row\_id ,\* FROM PLATZI.alumnos ORDER BY ID )STUDENT\_ROW WHERE ROW\_ID>1 )
Mi solucion del reto de la clase pasada: ```js DELETE FROM platzi.alumnos WHERE id = ( SELECT id FROM ( SELECT * FROM ( SELECT id, ROW_NUMBER() OVER( PARTITION BY nombre, apellido, email, colegiatura, fecha_incorporacion, carrera_id, tutor_id ORDER BY id ASC ) AS row--, --* FROM platzi.alumnos ) AS duplicados WHERE duplicados.row > 1 ) ); ```

Así mandé llamar los registros que el id de la carrera y del tutor se encuentre dentro del rango de intersección

<code> 
SELECT * FROM platzi.alumnos

WHERE

int4range (
	(SELECT MIN(carrera_id) FROM platzi.alumnos),
	(SELECT MAX (carrera_id) FROM platzi.alumnos)
)   @> tutor_id

or

int4range (
	(SELECT MIN(tutor_id) FROM platzi.alumnos),
	(SELECT MAX (tutor_id) FROM platzi.alumnos)
)   @> carrera_id
	;

SELECT int4range(10,20) * int4range(15,25) --[15,20)
SELECT int4range(10,30) * int4range(15,25) --[15,25)
SELECT int4range(15,25) * int4range(30,40) --ERROR
SELECT int4range(30,40) * int4range(15,25) --empty

Rango [15, 20)

  • Incluye: 15
  • Excluye: 20
SELECT numrange(11.5 , 19.9) && numrange(20.0 , 30.0) --FALSE
SELECT numrange(11.5 , 20.0) && numrange(20.0 , 30.0) --FALSE
SELECT numrange(11.5 , 20.1) && numrange(20.0 , 30.0) --TRUE 

smallint

  • 2 bytes
  • -32768 to +32767

integer

  • 4 bytes
  • -2147483648 to +2147483647
-- Relación de rangos entre tutores y carreras
SELECT  int4range(MIN(tutor_id), MAX(tutor_id)) *  int4range(MIN(carrera_id), MAX(carrera_id))
FROM platzi.alumnos;

Solución al reto:

SELECT int8range(MIN(carrera_id), MAX(carrera_id))* 
		int8range(MIN(tutor_id), MAX(tutor_id))
FROM platzi.alumnos;

Mi propuesta

SELECT int4range(min(tutor_id), max(tutor_id)) * int4range("min"(carrera_id), "max"(carrera_id))
FROM platzi.alumnos;

No enterndí el uso de

SELECT numrange(11.1, 19.9) && numrange(20.0, 30.0);

A qué se refiere con solapar?, unos número que se solapan qué es?

chequeate esta easy kill:

SELECT int4range(minimo_tutor,maximo_tutor) * int4range(minimo_carrera,maximo_carrera) AS interseccion
FROM (
		SELECT MIN(tutor_id) AS minimo_tutor, MAX(tutor_id) AS maximo_tutor, MIN(carrera_id) AS minimo_carrera, MAX(carrera_id) AS maximo_carrera
		FROM platzi.alumnos
) AS subconsulta;

Reto: extraer todos lo valores que hallan en comun entre los id de tutores y los id de carreras

SELECT *
FROM (
	SELECT 
	ROW_NUMBER() OVER() AS row_id, *
	FROM platzi.alumnos
) AS range_alumnos
WHERE carrera_id BETWEEN tutor_id AND tutor_id
	OR tutor_id BETWEEN carrera_id AND carrera_id;
SELECT id, carrera_id, tutor_id
from platzi.alumnos
where carrera_id = tutor_id;
SELECT (
	       int4range(MIN (carrera_id), MAX (carrera_id)) *
         int4range(MIN (tutor_id),   MAX (tutor_id))
        ) AS interseccion 
FROM platzi.alumnos;

Mi solución al reto:

Dado que hay 50 carreras y todos los tutores entran en alguna carrera, el mejor ejemplo sería traerme las carreras que se encuentren en los ids de Tutores, es decir, hasta 30.

SELECT *
FROM platzi.alumnos
WHERE carrera_id IN (
	SELECT DISTINCT tutor_id 
	FROM platzi.alumnos )
ORDER BY tutor_id, carrera_id;

DELETE FROM platzi.alumnos
WHERE id IN (
SELECT id
FROM platzi.alumnos
GROUP BY id
HAVING COUNT(*) > 1
)

así borré el duplicado

El reto:

SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id), MAX(carrera_id))
FROM platzi.alumnos;

–Otra forma de hacer el borrado del campo repetido
DELETE
FROM platzi.alumnos
WHERE id NOT IN (
SELECT id FROM (
SELECT id,
ROW_NUMBER() OVER(
PARTITION BY
nombre,
apellido,
email,
colegiatura,
fecha_incorporacion,
carrera_id,
tutor_id
ORDER BY id ASC
) AS row
FROM platzi.alumnos
) AS duplicados
WHERE duplicados.row > 1
);

SELECT int4range(min(carrera_id),max(carrera_id)) * int4range(min(tutor_id),max(tutor_id))
FROM platzi.alumnos;
SELECT * 
FROM platzi.alumnos
WHERE int4range (10, 50) @> tutor_id;

SELECT * 
FROM platzi.alumnos
WHERE int4range (10, 50) @> carrera_id; 
SELECT *
FROM platzi.alumnos
WHERE (
	SELECT int4range(MIN(carrera_id),MAX(carrera_id)) * int4range(MIN(tutor_id),MAX(tutor_id))
	FROM platzi.alumnos) @> tutor_id 
	AND (
	SELECT int4range(MIN(carrera_id),MAX(carrera_id)) * int4range(MIN(tutor_id),MAX(tutor_id))
	FROM platzi.alumnos) @> carrera_id 
	;

Mi respuesta al reto pero utilizando Max y Min

select alu from (
	select 
	int4range(min(a.tutor_id), max(a.tutor_id))
	* int4range(min(a.carrera_id), max(a.carrera_id)) as interseccion
	from alumnos a) as resumen, 
	alumnos alu
	where 
		interseccion @> alu.tutor_id
		and interseccion @> alu.carrera_id
	order by alu.carrera_id, alu.tutor_id;
SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(akumno_id), MAX(alumno_id))
FROM platzi.alumnos

En el delete no tuve mucho que poner ya que solo existen 2 registro de haber mas, considero que en el where pondria mas campos para que se tomen en cuenta

delete from platzi.alumnos where id = 1001

Reto

SELECT numrange(min(tutor_id), max(tutor_id)) * numrange(min(carrera_id), max(carrera_id))
FROM platzi.alumnos

Reto Anterior

DELETE
FROM platzi.alumnos
WHERE id IN (
SELECT id
FROM (
SELECT id,
ROW_NUMBER () OVER (
PARTITION BY
nombre, 
apellido,
email,
colegiatura, 
fecha_incorporacion,
carrera_id,
tutor_id
	ORDER BY id ASC
	)AS row
FROM platzi.alumnos
	)AS duplicados
	WHERE duplicados.row > 1);
	

RETO

SELECT int4range(MIN(tutor_id),MAX(tutor_id)) *
    int4range(MIN(carrera_id),MAX(carrera_id))
FROM platzi.alumnos
<code> 

Esta fue mi solución al reto:

SELECT numrange(
	(SELECT MIN(tutor_id) FROM platzi.alumnos),
	(SELECT MAX(tutor_id) FROM platzi.alumnos)
) * numrange(
	(SELECT MIN(carrera_id) FROM platzi.alumnos),
	(SELECT MAX(carrera_id) FROM platzi.alumnos)
);
--Solución para obtener  la intersección o elementos en común entre tutor_id y carrera_id

--Forma 1 :
SELECT numrange((SELECT MIN(tutor_id)
				FROM platzi.alumnos),
				(SELECT MAX(tutor_id)
					FROM platzi.alumnos)) * 
	   numrange((SELECT MIN(carrera_id)
					FROM platzi.alumnos),
				(SELECT MAX(carrera_id)
					FROM platzi.alumnos));

--Forma 2: 
SELECT int4range(( SELECT MIN(tutor_id)
					FROM platzi.alumnos), 
				(SELECT MAX(tutor_id)
					FROM platzi.alumnos)) *
	   int4range(( SELECT MIN(carrera_id)
					FROM platzi.alumnos), 
				(SELECT MAX(carrera_id)
					FROM platzi.alumnos));

En SQL Server:
– Borrado de arreglo de ID por partición por todos los campos –
DELETE FROM alumnos
WHERE id IN
(
SELECT id
FROM (
SELECT id,
ROW_NUMBER() OVER(
PARTITION BY
nombre,
apellido,
email,
colegiatura,
fecha_incorporacion,
carrera_id,
tutor_id
ORDER BY id asc
) AS row
FROM alumnos
) duplicados
WHERE duplicados.row > 1
);

/**

  • Rangos y solapes
    */

– Ejemplos iniciales –
SELECT *
FROM alumnos
WHERE tutor_id IN (11,12,13,14,15,16,17,18,19,20);

SELECT *
FROM alumnos
WHERE tutor_id >= 1
AND tutor_id <= 10;

SELECT *
FROM alumnos
WHERE tutor_id BETWEEN 1 AND 10;

– ¿En rango? –
SELECT 3
from alumnos
where tutor_id BETWEEN 10 AND 20;

– Filtrar alumnos cuyo tutor_id esté entre 1 y 10 –
SELECT *
FROM alumnos
WHERE tutor_id >= 10 AND tutor_id <= 20

RETO RESUELTO: Obtener el rango de IDs para tutores y el rango de los IDs de carreras .

SELECT int4range(MIN(tutor_id),MAX(tutor_id),'[]') AS rango_tutores,
	   int4range(MIN(carrera_id),MAX(carrera_id),'[]') AS rango_carreras
	   FROM platzi.alumnos

El rango de valores comunes para los IDs de tutores y de carreras

 int4range(MIN(tutor_id),MAX(tutor_id),'[]') AS rango_tutores *
 int4range(MIN(carrera_id),MAX(carrera_id),'[]') AS rango_carreras
-- Devuelve el rango de overlap que es [1,31)

Mostrar solo los alumnos en las que los IDs de tutor y de carrera estén dentro de este rango común

SELECT *
FROM platzi.alumnos
WHERE (SELECT 
	   int4range(MIN(tutor_id),MAX(tutor_id),'[]') *
	   int4range(MIN(carrera_id),MAX(carrera_id),'[]')
	   FROM platzi.alumnos  
	  ) @> carrera_id
;

Como podemos apreciar solo hay IDs de tutores y carreras entre [1,31) es decir del 1 al 30 (6043registros cumplen esa restricción)

Aclaración:

El int4range(a, b) genera el rango de valores enteros [a, b) es decir, incluye el valor inferior, pero excluye al valor superior.
Por ejemplo si hacemos las consultas:

SELECT int4range(10, 20);          -- Rango resultante es [10,20)    
SELECT int4range(10, 20) @> 10;    -- Devuelve true
SELECT int4range(10, 20) @> 20;    -- Devuelve false

Takeaway: Igual que la notación matemática de rangos, corchete incluye y paréntesis excluye a un valor.

Mi solución al reto:

 SELECT *
 FROM (
 	SELECT int4range(MIN(tutor_id),MAX(tutor_id)) * int4range(MIN(carrera_id),MAX(carrera_id))
 	FROM platzi.alumnos
 ) AS rangos_alumnos;

Lo que entendí es mostrar que valores de carrera_id están en el rango de valores de tutor_id o viceversa, basado en eso, esta es mi solución:

select distinct carrera_id from platzi.alumnos
where carrera_id in (select distinct tutor_id from platzi.alumnos);
DELETE FROM platzi.alumnos
	WHERE id IN(
		SELECT id
		FROM platzi.alumnos AS ou 
		WHERE ( 
			SELECT COUNT(*)
			FROM platzi.alumnos AS inr
			WHERE ou.email = inr.email
			) > 1
		OFFSET 1
		)

Mi solución al reto:

SELECT * FROM platzi.alumnos
WHERE tutor_id = carrera_id
ORDER BY tutor_id ASC;

Aunque no lo trae como rango si me trae los valores en común

SELECT DISTINCT carrera_id
FROM platzi.alumnos
WHERE carrera_id IN (
	SELECT tutor_id FROM platzi.alumnos
) ORDER BY carrera_id ASC;

segun mi logica esta es la solucion planteada desde un punto diferente

SELECT *
FROM platzi.alumnos
where tutor_id in (SELECT platzi.alumnos.tutor_id
				 from platzi.alumnos
				 GROUP BY(tutor_id)) and carrera_id in(SELECT platzi.alumnos.tutor_id
				 from platzi.alumnos
				 GROUP BY(tutor_id))

comparto mi solucion para encontrar el rango

select numrange(min(tutor_id), max (tutor_id)) * numrange (min(carrera_id),max (carrera_id))
from platzi.alumnos;
    

tambien realice este otro query para saber que alumnos tenian la clase con el mismo numero de tutor

SELECT id,carrera_id, tutor_id
FROM platzi.alumnos
WHERE tutor_id = carrera_id
order by tutor_id;

RETO
Seleccionar el rango de numeros de los valores que hay en común entre los id’s de tutores y carreras.


SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id), MAX(carrera_id))
FROM platzi.alumnos;

– Rangos en común entre tutores y carreras

select 
	numrange(MIN(tutor_id), MAX(tutor_id)) * numrange(MIN(carrera_id), MAX(carrera_id)) as en_comun, 
	numrange(MIN(tutor_id), MAX(tutor_id)) as rago_turores, 
	numrange(MIN(carrera_id), MAX(carrera_id)) as rango_carreras 
from 
	platzi.alumnos

Yo lo solucione de está forma

SELECT *
FROM platzi.alumnos
WHERE tutor_id IN (carrera_id);

SELECT INT4RANGE (MIN (tutor_id), MAX(tutor_id)) *
INT4RANGE (MIN (carrera_id), MAX(carrera_id))
FROM platzi_alumnos;

Con la Query SELECT *
FROM platzi.alumnos
WHERE int4range(10,20) @>tutor_id; arroja 347 registros, por el contrario con la query SELECT *
FROM platzi.alumnos
WHERE tutor_id BETWEEN 10 AND 20; arroja 383 registros, creo que esto se debe a que con la primera no tiene en cuenta los tutores id=20, con la segunda si

Muchas gracias por la clase!

Hola! comparto mi solucion del reto:

SELECT 
	int4range(MIN(carrera_id), MAX(carrera_id))
     * int4range(MIN(tutor_id), MAX(tutor_id))
FROM platzi.alumnos

Solución al reto
Rango de valores en comun entre los ID de carreras y tutor

select int4range(min(rango), max(rango))
from(
	select tutor_id as Rango
	from platzi.alumnos
	where tutor_id = carrera_id) as rangos_tabla;

Solución al reto:

SELECT int4range(MIN(carrera_id), MAX(carrera_id)) * int4range(MIN(tutor_id),MAX(tutor_id))
FROM platzi.alumnos

resultado [1,30)

Yo no recomendaría hacer un DELETE con la sentencia IN (DELETE FROM table WHERE id IN), ya que puede llegar a pasar que borramos más de una tupla.
Por lo tanto, yo aconsejaría hacer una de las siguientes dos cosas:

  • Si usas la sentencia IN, agrega el LIMIT 1
  • De otra forma, hazlo de la siguiente manera DELETE FROM table WHERE id = condition
SELECT 
numrange (MIN(tutor_id), MAX(tutor_id)) 
FROM (
	SELECT DISTINCT(tutor_id)
	FROM platzi.alumnos
	WHERE tutor_id = carrera_id
	ORDER BY tutor_id ASC
) AS rango
;

Aquí les dejo mi solución al reto:

SELECT 
int4range((SELECT MIN(carrera_id) FROM platzi.alumnos), (SELECT MAX(carrera_id) FROM platzi.alumnos)) *
int4range((SELECT MIN(tutor_id) FROM platzi.alumnos), (SELECT MAX(tutor_id) FROM platzi.alumnos));
--Modo 1:
SELECT int4range(MIN(tutor_id), MAX(tutor_id)) * int4range(MIN(carrera_id), MAX(carrera_id)) AS interseccion
FROM platzi.alumnos;

--Modo 2:
SELECT 
	numrange(min_carrera, max_carrera) * numrange(min_tutor, max_tutor) AS interseccion
FROM (
	SELECT 
		MIN(carrera_id) as min_carrera,
		MAX(carrera_id) as max_carrera,
		MIN(tutor_id) as min_tutor,
		MAX(tutor_id) as max_tutor
	FROM platzi.alumnos
) AS rangos;

Posible Respuesta:

SELECT  int4range( (SELECT MIN(carrera_id) FROM platzi.alumnos), 
(SELECT MAX(carrera_id) FROM platzi.alumnos)) * int4range(
				(SELECT MIN(tutor_id) FROM platzi.alumnos), 
(SELECT MAX(tutor_id) FROM platzi.alumnos));

Primero busque los MAX y MIN de los campos carrera_id y tutor_id con

SELECT MAX/MIN ()
FROM platzi.alumnos

Luego con el comando de calculo de intersección saco el conjunto en comun entre ambos reemplazando la querys donde van el max y min de tutor_id y carrera_id

SELECT int4range(,) * int4range(,);

Finalmente con esto armado, filtro por el conjunto obtenido
reemplazando en valor la query anterior que ya me va a arrojar un conjunto

SELECT *
FROM platzi.alumnos
WHERE int4range(,) @> tutor_id;

Resultado final:

SELECT *
FROM platzi.alumnos
WHERE int4range((SELECT int4range(
					(SELECT MIN (carrera_id)
					FROM platzi.alumnos), (
					SELECT MAX (carrera_id)
					FROM platzi.alumnos)) 
				* int4range(
					(SELECT MIN (tutor_id)
					FROM platzi.alumnos),
					(SELECT MAX (tutor_id)
					FROM platzi.alumnos)))
) @> tutor_id;

Hola, esta fue mi solucion parcial al reto:

SELECT *
FROM platzi.alumnos
WHERE alumnos.tutor_id<@(
	SELECT (int4range(MIN(tutor_id),MAX(tutor_id)) * int4range(MIN(carrera_id),MAX(carrera_id))) AS valores_comunes
	FROM platzi.alumnos
SELECT int4range(MIN(carrera_id),MAX(carrera_id), '[]') * int4range(MIN(tutor_id),MAX(tutor_id), '[]') AS intersección_ids
FROM platzi.alumnos;
--Aporte desde MySQL
SELECT a.tutor_id,b.carrera_id
FROM alumnos as a
inner JOIN alumnos as b
ON a.tutor_id = b.carrera_id
group by a.tutor_id
order by a.tutor_id;

Mi Reto:

select * 
from platzi.alumnos
where tutor_id = carrera_id;

Mi solución al reto. No creo que sea muy práctico pero jala.

SELECT *
FROM platzi.alumnos
WHERE (
	SELECT UPPER(int8range(0, tutor_id))
) = carrera_id;