SQL - Consulta: Mostrar de a dos datos

 
Vista:

Consulta: Mostrar de a dos datos

Publicado por Mc (3 intervenciones) el 22/11/2014 01:07:30
Hola, tengo el siguiente ejercicio de sql que no pude resolver.

Mostrar una lista de a pares, de todos los fabricantes que fabriquen el mismo producto.
En el caso que haya un único fabricante deberá mostrar el Código de fabricante 2 en nulo.


El listado tiene que tener el siguiente formato:

Nro. de Producto(stock_num) - Descripc. del producto(Description) - Cód. defabric. 1(manu_code) - Cód. defabric. 2(manu_code)


La tabla que contiene los datos es la siguiente:

-----------------------------
STOCK
-----------------------------

stock_num (PK) -> Código de Producto
manu_code (PK) -> Código de Fabricante
descripcion -> Descripcion del producto


Alguien podría ayudarme con este ejercicio?
No se me ocurre cómo resolverlo, ya que un mismo producto puede tener más de dos fabricantes.

Gracias!
Valora esta pregunta
Me gusta: Está pregunta es útil y esta claraNo me gusta: Está pregunta no esta clara o no es útil
0
Responder
sin imagen de perfil
Val: 806
Bronce
Ha mantenido su posición en SQL (en relación al último mes)
Gráfica de SQL

Consulta: Mostrar de a dos datos

Publicado por leonardo_josue (1173 intervenciones) el 24/11/2014 17:03:59
Hola Mc:

Te recuerdo en primer lugar que aquí no hacemos tareas de otras personas... En tu post no nos dices qué intentaste hacer, (porque supongo que intentaste hacer algo ¿verdad?) No vale decir que no se te ocurre cómo resolverlo, lo menos que pedimos es un poco de esfuerzo de parte de los foristas para poder ayudarlos.

Hay muchas maneras de resolver este ejercicio... por ejemplo mediante subconsultas, procedimientos almacenados, o la más simple, con un LEFT JOIN...

El LEFT JOIN, lo debes hacer sobre la misma tabla, cuidando únicamente que sea el mismo producto, pero un fabricante distinto... checa este ejemplo:

1
2
3
4
5
6
7
8
9
10
11
mysql> SELECT * FROM stock;
+-----------+-----------+---------------+
| stock_num | manu_code | descripcion   |
+-----------+-----------+---------------+
|         1 |         1 | producto uno  |
|         1 |         2 | producto uno  |
|         2 |         1 | producto dos  |
|         3 |         2 | producto tres |
|         3 |         3 | producto tres |
+-----------+-----------+---------------+
5 rows in set (0.00 sec)

Aquí se observa que los productos uno y tres tienen dos fabricantes... mientras que el producto 2 sólo tiene un fabricante... Con un simple LEFT JOIN puedes obtener esto:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
mysql> SELECT S1.stock_num, S1.descripcion,
    -> S1.manu_code 'Cód. defabric. 1', S2.manu_code 'Cód. defabric. 2'
......
......
......
+-----------+---------------+-------------------+-------------------+
| stock_num | descripcion   | Cód. defabric. 1  | Cód. defabric. 2  |
+-----------+---------------+-------------------+-------------------+
|         1 | producto uno  |                 1 |                 2 |
|         1 | producto uno  |                 2 |                 1 |
|         3 | producto tres |                 3 |                 2 |
|         3 | producto tres |                 2 |                 3 |
|         2 | producto dos  |                 1 |              NULL |
+-----------+---------------+-------------------+-------------------+
5 rows in set (0.00 sec)

Obviamente no estoy colocando el LEFT, pues eso lo tienes que obtener por tu cuenta... haz algunas pruebas y nos comentas. Incluso puedes omitir los resultados "repetidos" es decir, dejar sólo un registro por producto:

1
2
3
4
5
6
7
8
9
10
11
12
mysql> SELECT S1.stock_num, S1.descripcion,
    -> S1.manu_code 'Cód. defabric. 1', S2.manu_code 'Cód. defabric. 2'
.......
........
+-----------+---------------+-------------------+-------------------+
| stock_num | descripcion   | Cód. defabric. 1  | Cód. defabric. 2  |
+-----------+---------------+-------------------+-------------------+
|         1 | producto uno  |                 1 |                 2 |
|         3 | producto tres |                 2 |                 3 |
|         2 | producto dos  |                 1 |              NULL |
+-----------+---------------+-------------------+-------------------+
3 rows in set (0.00 sec)

Haz la prueba y nos comentas. Si continuas con problemas, postea algo del código que probaste, dinos qué problemas/errores tuviste y con gusto te ayudamos a corregirlo.

Saludos
Leo
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
1
Comentar

Consulta: Mostrar de a dos datos

Publicado por Mc (3 intervenciones) el 24/11/2014 20:05:34
Hola Leo:

En primer lugar, te agradezco por tomarte el tiempo para contestar.

Te cuento que no lo intenté previamente ya que no sabía por donde empezar a encararlo. No preguntaba para que me "hicieran una tarea" sino para poder aprender.

Gracias a la ayuda de otros, pude resolverlo utilizando common table expression y
ROW_NUMBER ( ) OVER ( [ PARTITION BY value_expression , ... [ n ] ] order_by_clause ).

Saludos!
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar
sin imagen de perfil
Val: 806
Bronce
Ha mantenido su posición en SQL (en relación al último mes)
Gráfica de SQL

Consulta: Mostrar de a dos datos

Publicado por leonardo_josue (1173 intervenciones) el 24/11/2014 21:10:39
Hola de nuevo MC...

Mi intención no era regañarte, sino hacerte notar que tal como redactaste tu post tal pareciera que pretendías que hicieramos tu trabajo (muchas veces hemos tenido este problema con anterioridad)...

Me da gusto que hayas encontrado la respuesta con alguien más y te pediría que compartieras la solución final, ya que me parece interesante saber cómo utilizaste la función ROW_NUMBER para este caso, así si alguien más tiene el mismo problema, pueda saber cómo resolverlo.

También te pediría que compartieras con el foro el DBMS con el que estás trabajando, ya que la función ROW_NUMBER no es soportada por todos (MySQL por ejemplo no la tiene), por eso en mi post mencionaba que hay muchas formas de llegar a la consulta, pero la manera "estandar" sería con el uso de LEFT JOIN:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
mysql> SELECT * FROM stock;
+-----------+-----------+---------------+
| stock_num | manu_code | descripcion   |
+-----------+-----------+---------------+
|         1 |         1 | producto uno  |
|         1 |         2 | producto uno  |
|         2 |         1 | producto dos  |
|         3 |         2 | producto tres |
|         3 |         3 | producto tres |
+-----------+-----------+---------------+
5 rows in set (0.00 sec)
 
mysql> SELECT S1.stock_num, S1.descripcion, S1.manu_code 'Cód. defabric. 1', S2.manu_code 'Cód. defabric. 2'
    -> FROM stock S1
    -> LEFT JOIN stock S2 ON S1.stock_num = S2.stock_num AND S1.manu_code != S2.manu_code
    -> WHERE S1.manu_code < S2.manu_code OR s2.manu_code IS NULL;
 
+-----------+---------------+-------------------+-------------------+
| stock_num | descripcion   | Cód. defabric. 1  | Cód. defabric. 2  |
+-----------+---------------+-------------------+-------------------+
|         1 | producto uno  |                 1 |                 2 |
|         3 | producto tres |                 2 |                 3 |
|         2 | producto dos  |                 1 |              NULL |
+-----------+---------------+-------------------+-------------------+
3 rows in set (0.00 sec)

Saludos
Leo
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

Consulta: Mostrar de a dos datos

Publicado por Mc (3 intervenciones) el 25/11/2014 16:12:49
Hola, les dejo la solución final para SQL SERVER y el link de la conversación del foro de MSDN.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
WITH C1 AS (
			SELECT	*,
				(ROW_NUMBER() OVER(PARTITION BY stock_num ORDER BY manu_code) - 1) / 2 AS grp
			  FROM	stock
		)
		, C2 AS (
			SELECT	*,
				ROW_NUMBER() OVER(PARTITION BY stock_num, grp ORDER BY manu_code) AS rn
			  FROM	c1
		)
		SELECT	stock_num,
				[description],
				MIN(CASE WHEN rn = 1 THEN manu_code END) AS manu_code1,
				MAX(CASE WHEN rn = 2 THEN manu_code END) AS manu_code2
		  FROM	C2
	          GROUP BY stock_num,
			   [description],
	                   grp;

https://social.msdn.microsoft.com/Forums/es-ES/319158e1-4ce0-4d1c-adb5-b72136fb1784/cmo-podra-resolver-este-select-mostrar-datos-en-dos-columnas?forum=sqlserveres

Saludos
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
1
Comentar
Imágen de perfil de xve
Val: 135
Ha mantenido su posición en SQL (en relación al último mes)
Gráfica de SQL

Consulta: Mostrar de a dos datos

Publicado por xve (284 intervenciones) el 25/11/2014 22:18:48
Gracias por compartirlo!!!
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar