NIA

Anuncio
!
!
PHP
Introducción a las
Bases de Datos
Área de Ingeniería Telemática
Dpto. Automática y Computación
http://www.tlm.unavarra.es/
Almacenando información
‣ Ficheros??
‣ DBMS (DataBase Managemente System)
‣ Masivo (TB)
‣ Persistente
‣ Seguro ‣ Multi-usuario (acceso concurrente)
‣ Conveniente (data independence y lenguaje de petición)
‣ Eficiente (queries/s)
‣ Fiable (99.9% uptime)
!
‣ Genérico y accesible desde diferentes lenguajes
Modelo relacional
‣ Usado en todos los sistemas de DB actuales
‣ Modelo muy simple
‣ Peticiones en lenguaje de alto nivel
SQL : Structured Query Language
‣ Implementaciones muy eficientes
No confundir
‣ SQL: Structured Query Language
!
‣ Gestores de bases de datos (DBMS)
‣ MySQL <<< usaremos este
‣ PostgreSQL
‣ Oracle
‣ Sqlite
‣ ...
El modelo
‣ Una base de datos es un conjunto de tablas o relaciones
‣ Tablas/Relaciones
‣ Esquema
estudios { NIA, Carrera, CredSuperados }
personas { NIA, Nombre, Lugar, Foto }
personas
estudios
NIA
Nombre
Lugar
Foto
NIA
Carrera
CredSuperados
51242
Juan
Madrid
f1223.png
51242
Informatica
40
61623
Ane
Pamplona
f2662.png
61623
Fisica
42
11112
Bob
New York
f4233.png
11112
null
50
23212
Juan
Madrid
null
23212
Historia
0
77172
Cristina
Barcelona
f2111.png
77172
Informatica
30
...
...
El modelo
‣ La base de datos es un conjunto de relaciones (o tablas)
‣ La relación tiene un conjunto de atributos con nombre (columnas) ‣ Cada tupla (o fila) es tiene un valor para cada atributo
‣ Cada atributo tiene un tipo (o dominio)
personas
estudios
NIA
Nombre
Lugar
Foto
NIA
Carrera
CredSuperados
51242
Juan
Madrid
f1223.png
51242
Informatica
40
61623
Ane
Pamplona
f2662.png
61623
Fisica
42
11112
Bob
New York
f4233.png
11112
null
50
23212
Juan
Madrid
null
23212
Historia
0
77172
Cristina
Barcelona
f2111.png
77172
Informatica
30
...
...
El modelo
‣ Los atributos que llamamos key (clave) no pueden tener dos filas
con el mismo valor
‣ Hay atributos que pueden tener un valor indefinido: NULL
‣ Hay atributos que pueden incrementarse automáticamente cada
vez que insertamos una fila
personas
estudios
NIA
Nombre
Lugar
Foto
NIA
Carrera
CredSuperados
51242
Juan
Madrid
f1223.png
51242
Informatica
40
61623
Ane
Pamplona
f2662.png
61623
Fisica
42
11112
Bob
New York
f4233.png
11112
null
50
23212
Juan
Madrid
null
23212
Historia
0
77172
Cristina
Barcelona
f2111.png
77172
Informatica
30
...
...
Creando tablas
‣ Lenguaje SQL
CREATE TABLE Personas ( NIA, Nombre, Lugar, Foto )
CREATE TABLE Estudios ( NIA, Carrera, CredSuperados )!
Con tipos
CREATE TABLE Personas ( !
NIA integer,!
Nombre varchar(20), !
Lugar varchar(50),!
Foto varchar(50)!
);!
CREATE TABLE Estudios (!
NIA integer, Carrera varchar(50), CredSuperados integer!
);!
INSERT INTO Personas (NIA,Nombre,Lugar,Foto)
!
VALUES (11112,"Bob","New York","f4233.png");!
INSERT INTO Estudios (NIA,Carrera,CredSuperados)
!
VALUES (77172,"Informatica",30);
Usando un DBMS
‣ Servidor de bases de datos
‣ Usando el comando mysql
!
!
$ mysql -u mikel -p !
!
!
‣ Con mysql a un host remoto
$ mysql -u mikel -p !
Enter password: !
Welcome to the MySQL monitor.
…!
mysql> use mikel;!
Database changed!
mysql> show tables;!
+-----------------+!
| Tables_in_mikel |!
+-----------------+!
| Estudios
|!
| prueba
|!
+-----------------+!
2 rows in set (0.00 sec)!
Commands end with ; or \
!
mysql> select * from prueba;!
+------------+-------+-------+!
| nombre
| nia
| foto |!
+------------+-------+-------+!
| Alice
| 22212 | s.png |!
| Caschar
| 50045 |
|!
+------------+-------+-------+!
2 rows in set (0.00 sec)
!
!
$ mysql -u mikel -p -h 10.1.1.36 -P 3307
!
‣ Usando un gestor como PHPMyAdmin
‣ Demo
Obteniendo información
‣ Create Read Update Delete
‣ Orden SELECT
SELECT campos FROM tabla [ WHERE condiciones ]
mysql> SELECT * FROM Personas;!
+-------+----------+-----------+-----------+!
| NIA
| Nombre
| Lugar
| Foto
|!
+-------+----------+-----------+-----------+!
| 51242 | Juan
| Madrid
| f1223.png |!
| 61623 | Ane
| Pamplona | f2662.png |!
| 11112 | Bob
| New York | f4233.png |!
| 23212 | Juan
| Madrid
| NULL
|!
| 77172 | Cristina | Barcelona | f2111.png |!
+-------+----------+-----------+-----------+!
5 rows in set (0.08 sec)!
mysql> SELECT NIA,Nombre FROM Personas;!
+-------+----------+!
| NIA
| Nombre
|!
+-------+----------+!
| 51242 | Juan
|!
| 61623 | Ane
|!
| 11112 | Bob
|!
| 23212 | Juan
|!
Obteniendo información
‣ Incluyendo condiciones sobre los campos
SELECT campos FROM tabla
WHERE condiciones
mysql> SELECT * FROM Estudios WHERE Carrera="informatica";!
+-------+-------------+---------------+!
| NIA
| Carrera
| CredSuperados |!
+-------+-------------+---------------+!
| 51242 | Informatica |
40 |!
| 77172 | Informatica |
30 |!
+-------+-------------+---------------+!
2 rows in set (0.00 sec)!
!
mysql> SELECT * FROM Estudios!
-> WHERE Carrera="Informatica" and CredSuperados>30;!
+-------+-------------+---------------+!
| NIA
| Carrera
| CredSuperados |!
+-------+-------------+---------------+!
| 51242 | Informatica |
40 |!
+-------+-------------+---------------+!
1 row in set (0.00 sec)!
!
SELECT avanzado...
‣ Usando varias tablas para obtener un resultado
!
!
!
!
!
mysql> SELECT NIA,Nombre,CredSuperados !
-> FROM Personas natural join Estudios!
-> WHERE carrera="Informatica" and credsuperados>30;!
+-------+--------+---------------+!
| NIA
| Nombre | CredSuperados |!
+-------+--------+---------------+!
| 51242 | Juan
|
40 |!
+-------+--------+---------------+!
1 row in set (0.00 sec)!
‣ Ordenando los resultados
mysql> SELECT * FROM Estudios ORDER BY CredSuperados DESC;!
+-------+-------------+---------------+!
| NIA
| Carrera
| CredSuperados |!
+-------+-------------+---------------+!
| 11112 | NULL
|
50 |!
| 61623 | Fisica
|
42 |!
| 51242 | Informatica |
40 |!
| 77172 | Informatica |
30 |!
| 23212 | Historia
|
0 |!
+-------+-------------+---------------+!
5 rows in set (0.00 sec)!
Modificando
‣ Insertar
INSERT INTO tabla (campos) VALUES (valores);
!
mysql>
INSERT INTO Personas (NIA,Nombre,Lugar) VALUES (11112,"Mikel","Pamplona")
ERROR 1062 (23000): Duplicate entry '11112' for key 'PRIMARY'!
mysql>
INSERT INTO Personas (NIA,Nombre,Lugar) VALUES (32111,"Mikel","Pamplona")
!
Query OK, 1 row affected (0.00 sec)!
! !
‣ Borrar entradas
DELETE FROM tabla WHERE condiciones;
mysql>
DELETE FROM Personas WHERE Foto IS NULL;!
!
Query OK, 2 rows affected (0.01 sec)!
!!
‣ Borrar tablas
mysql> TRUNCATE TABLE Estudios;!
Query OK, 0 rows affected (0.05 sec)!
Borra el contenido
mysql> DROP TABLE Estudios;!
Query OK, 0 rows affected (0.01 sec)!
Borra la tabla
Modificando
‣ UPDATE tabla SET valoresnuevos WHERE condiciones;
mysql> UPDATE Personas SET Foto="f5512.png" WHERE NIA=23212;!
Query OK, 1 row affected (0.02 sec)!
Rows matched: 1 Changed: 1 Warnings: 0!
!
mysql> SELECT * FROM Personas;!
+-------+----------+-----------+-----------+!
| NIA
| Nombre
| Lugar
| Foto
|!
+-------+----------+-----------+-----------+!
| 51242 | Juan
| Madrid
| f1223.png |!
| 61623 | Ane
| Pamplona | f2662.png |!
| 11112 | Bob
| New York | f4233.png |!
| 23212 | Juan
| Madrid
| f5512.png |!
| 77172 | Cristina | Barcelona | f2111.png |!
+-------+----------+-----------+-----------+!
5 rows in set (0.00 sec)!
En resumen
‣ Bases de datos relacionales
‣ Gestores de bases de datos (DBMS)
‣ Lenguaje de peticiones a bases de datos (SQL)
‣ Operaciones básicas
‣ SELECT
‣ Crear tablas
‣ INSERT, DELETE, UPDATE
!
‣ Atributos especiales
‣ Primary keys
‣ Campos con autoincremento
Tipos de datos
‣ Tipos de datos numericos
INTEGER o INT...
FLOAT, REAL ... ‣ Fecha y hora
DATETIME, DATE, TIME, TIMESTAMP
‣ Cadenas
CHAR(n) cadena de texto de n caracteres
VARCHAR(n) cadena de texto de hasta n caracteres
BINARY(n) cadena de n bytes
VARBINARY(n) cadena de hasta n bytes
Tipos de datos
‣ Objetos de gran tamaño (como contenido de ficheros...)
‣ Se almacenan aparte y no con el resto de la fila.
VARCHAR es mas rapido si el tamaño es razonable...
BLOB/TEXT es mas comodo para objetos arbitrariamente
grandes
‣ Tipos
TINYBLOB / TINYTEXT (max256B)
BLOB / TEXT (max 65kB)
MEDIUMBLOB / MEDIUMTEXT (max 16MB)
LONGBLOB / LONGTEXT (max 4GB)
Tipos de datos
‣ ENUM( valores ) un valor entre varios
un conjuntos de valores
‣ SET( valores )
Maximo 64 valores posibles
!
CREATE TABLE persona (
! nombre VARCHAR(50),
! rol ENUM( 'admin' , 'teacher' , 'student' ),
)
!
CREATE TABLE persona (
! nombre VARCHAR(50),
! rol SET( 'admin' , 'teacher' , 'student' ),
)
Mas información sobre SQL
‣ http://dev.mysql.com/
‣ http://dev.mysql.com/doc/refman/5.5/en/index.html
Demo
‣ Ejemplos: SELECT con condiciones
describe alumnos;
select * from alumnos ;
select nia, nombre, apellidos from alumnos;
select nia, nombre, apellidos from alumnos order by nia;
select nia, nombre, apellidos from alumnos limit 10;
select nia, nombre, apellidos from alumnos limit 0,5;
select nia, nombre, apellidos from alumnos limit 5,5;
select nia, nombre, apellidos from alumnos where nia<65000;
select nia, nombre, apellidos from alumnos where nombre like 'M%';
select nia, nombre, apellidos from alumnos where nombre like 'Mi%';
select nia, nombre, apellidos from alumnos where nombre like '% %';
select count(*) from alumnos where nombre like '% %';
select nia, nombre, apellidos from alumnos order by rand();
select nia, nombre, apellidos from alumnos order by rand() limit 3;
!
!
BD
Combinando tablas
Área de Ingeniería Telemática
Dpto. Automática y Computación
http://www.tlm.unavarra.es/
BD
‣ Usando varias tablas
‣ Ejemplo:
!mysql>
select * from asignaturas;!
+-------+--------+----------+--------------------+---------------+!
| gradonalumnos |!
!| aid | nombre | nalumnos | gradonombre
+-------+--------+----------+--------------------+---------------+!
| 20209 | RC
|
20 | Informatica
|
300 |!
!| 10312 | SWS
|
50 | Telecomunicaciones |
400 |!
| 10314 | SWC
|
53 | Telecomunicaciones |
400 |!
70 | Telecomunicaciones |
400 |!
!| 10203 | ARSS |
| 20206 | AR
|
30 | Informatica
|
300 |!
+-------+--------+----------+--------------------+---------------+!
!
!
!
!
mysql> select * from asignaturas;!
+-------+------------+--------------+------+!
| aid
| asignatura | matriculados | gid |!
+-------+------------+--------------+------+!
| 20209 | RC
|
20 |
2 |!
| 20206 | AR
|
30 |
2 |!
| 10312 | SWS
|
50 |
1 |!
| 10314 | SWC
|
53 |
1 |!
| 10203 | ARSS
|
70 |
1 |!
+-------+------------+--------------+------+!
!!
‣ ¿Cual tiene más sentido?
mysql> select * from grados;!
+-----+--------------------+----------+!
| gid | grado
| nalumnos |!
+-----+--------------------+----------+!
|
2 | Informatica
|
300 |!
|
1 | Telecomunicaciones |
400 |!
|
3 | Fisica
|
42 |!
+-----+--------------------+----------+!
Obteniendo información de varias tablas
‣ JOIN para unir tablas
!
!
!
!
!
!
!
!
!
mysql> SELECT * FROM grados JOIN asignaturas;!
+-----+--------------------+----------+-------+------------+--------------+------+!
| gid | grado
| nalumnos | aid
| asignatura | matriculados | gid |!
+-----+--------------------+----------+-------+------------+--------------+------+!
|
2 | Informatica
|
300 | 20209 | RC
|
20 |
2 |!
|
1 | Telecomunicaciones |
400 | 20209 | RC
|
20 |
2 |!
|
3 | Fisica
|
42 | 20209 | RC
|
20 |
2 |!
|
2 | Informatica
|
300 | 20206 | AR
|
30 |
2 |!
|
1 | Telecomunicaciones |
400 | 20206 | AR
|
30 |
2 |!
|
3 | Fisica
|
42 | 20206 | AR
|
30 |
2 |!
|
2 | Informatica
|
300 | 10312 | SWS
|
50 |
1 |!
|
1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |
1 |!
|
3 | Fisica
|
42 | 10312 | SWS
|
50 |
1 |!
|
2 | Informatica
|
300 | 10314 | SWC
|
53 |
1 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |
1 |!
|
3 | Fisica
|
42 | 10314 | SWC
|
53 |
1 |!
|
2 | Informatica
|
300 | 10203 | ARSS
|
70 |
1 |!
|
1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |
1 |!
|
3 | Fisica
|
42 | 10203 | ARSS
|
70 |
1 |!
+-----+--------------------+----------+-------+------------+--------------+------+!
!
‣ Producto cartesiano todas las combinaciones
Aplicando condiciones al JOIN
‣ table1 JOIN table2 ON table1.campo = table2.campo
!
mysql>
select * from grados join asignaturas on grados.gid = asignaturas.gid;!
+-----+--------------------+----------+-------+------------+--------------+------+!
| gid | grado
| nalumnos | aid
| asignatura | matriculados | gid |!
!
+-----+--------------------+----------+-------+------------+--------------+------+!
|
2 | Informatica
|
300 | 20209 | RC
|
20 |
2 |!
|! 2 | Informatica
|
300 | 20206 | AR
|
30 |
2 |!
|
1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |
1 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |
1 |!
|! 1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |
1 |!
+-----+--------------------+----------+-------+------------+--------------+------+!
!
‣ table1 JOIN table2 USING(campo)
mysql> select * from grados join asignaturas using(gid);!
+-----+--------------------+----------+-------+------------+--------------+!
| gid | grado
| nalumnos | aid
| asignatura | matriculados |!
+-----+--------------------+----------+-------+------------+--------------+!
|
2 | Informatica
|
300 | 20209 | RC
|
20 |!
|
2 | Informatica
|
300 | 20206 | AR
|
30 |!
|
1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |!
|
1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |!
+-----+--------------------+----------+-------+------------+--------------+!
!
Natural JOIN
‣ JOIN con todos los campos que se llamen igual
!
mysql>
select * from grados natural join asignaturas;!
+-----+--------------------+----------+-------+------------+--------------+!
! | grado
| gid
| nalumnos | aid
| asignatura | matriculados |!
+-----+--------------------+----------+-------+------------+--------------+!
| ! 2 | Informatica
|
300 | 20209 | RC
|
20 |!
|
2 | Informatica
|
300 | 20206 | AR
|
30 |!
| ! 1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |!
| ! 1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |!
+-----+--------------------+----------+-------+------------+--------------+!
!
‣ Cuidado, podría haber campos que se llamen igual pero no
nos interese identificar (si matriculados se llamara nalumnos
por ejemplo)
Implicit JOIN
‣ Se puede escribir también....
mysql> select *!
-> from grados, asignaturas!
-> where grados.gid = asignaturas.gid AND matriculados > 40;!
+-----+--------------------+----------+-------+------------+--------------+------+!
| gid | grado
| nalumnos | aid
| asignatura | matriculados | gid |!
+-----+--------------------+----------+-------+------------+--------------+------+!
|
1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |
1 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |
1 |!
|
1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |
1 |!
+-----+--------------------+----------+-------+------------+--------------+------+!
!
Mas avanzados...
‣ Se pueden añadir condiciones
mysql> select *!
-> from grados join asignaturas!
-> on grados.gid = asignaturas.gid!
-> where matriculados > 40 ;!
+-----+--------------------+----------+-------+------------+--------------+------+!
| gid | grado
| nalumnos | aid
| asignatura | matriculados | gid |!
+-----+--------------------+----------+-------+------------+--------------+------+!
|
1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |
1 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |
1 |!
|
1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |
1 |!
+-----+--------------------+----------+-------+------------+--------------+------+!
Mas avanzados...
‣ LEFT y RIGHT OUTER JOINs
mysql> SELECT * FROM grados LEFT OUTER JOIN asignaturas USING (gid);!
+-----+--------------------+----------+-------+--------+----------+!
| gid | nombre
| nalumnos | aid
| nombre | nalumnos |!
+-----+--------------------+----------+-------+--------+----------+!
|
2 | Informatica
|
300 | 20209 | RC
|
20 |!
|
2 | Informatica
|
300 | 20206 | AR
|
30 |!
|
1 | Telecomunicaciones |
400 | 10312 | SWS
|
50 |!
|
1 | Telecomunicaciones |
400 | 10314 | SWC
|
53 |!
|
1 | Telecomunicaciones |
400 | 10203 | ARSS
|
70 |!
|
3 | Fisica
|
42 | NULL | NULL
|
NULL |!
+-----+--------------------+----------+-------+--------+----------+!
Para que vale esto?
‣ Normalmente no todo está en una tabla
usuarios ( userid, nombre, pass, foto )
SELECT userid, nombre, pass, foto FROM usuarios WHERE userid=X
!
mensajes ( userid, tiempo, mensaje )
Si quiero imprimir los mensajes con formato
nombre > mensaje
SELECT userid, tiempo, mensaje FROM mensajes ...
!
SELECT nombre, tiempo, mensaje
FROM usuarios JOIN mensajes USING (userid)
WHERE ...
Descargar