Curso sobre Visual Basic
por Guillermo Llanderas

Tercera Parte


Los temas incluidos:


Ejemplos de como crear una Base de Datos en runtime

> Creación de Bases de Datos en RunTime.

  '
  'Procedimiento para crear una DB y tablas asociadas en runtime
  '

  Const DbPath As String = "acuario2.mdb"

  'Definición de la Base de Datos
  Dim NewDb As Database
  Dim Ws As Workspace
    'Primero se crea un espacio de trabajo
  Set Ws = DBEngine.Workspaces(0)
  Dim DbOpciones As Long
    'la DB será en formato Access 2.0 y estará encriptada
  DbOpciones = dbVersion20 + dbEncrypt
    'Esto crea la DB
  Set NewDb = Ws.CreateDatabase(DbPath, dbLangGeneral, DbOpciones)

  'Definición de una tabla
  Dim NewTb As TableDef
    'Aquí se crea una tabla en el DB
  Set NewTb = NewDb.CreateTableDef("Articulos")
    'Se establece una normativa en la tabla que es que la cantidad mínima a
    'tener debe de ser mayor o igual a 0
  NewTb.ValidationRule = "CantidadMinima >= 0"
    'Mensaje de error si no se cumple la regla anterior
  NewTb.ValidationText = "La cantidad mínima debe ser mayor o igual a 0"

  'Definición de los campos de la tabla
    'La tabla de artículos va a constar de 7 campos diferentes
  ReDim Campo(1 To 9) As Field
    'Definición del primer campo de la tabla
  Set Campo(1) = NewTb.CreateField("Articulo", dbLong)
    'Idem del segundo campo
  Set Campo(2) = NewTb.CreateField("Descripcion", dbText, 50)
    'Idem del tercer campo. Las propiedades se establecen de forma explícita,
    'en vez de usar los argumentos de CreateField
  Set Campo(3) = NewTb.CreateField()
  Campo(3).Name = "Categoria"
  Campo(3).Type = dbText
  Campo(3).Size = 10
  Set Campo(4) = NewTb.CreateField("Mayorista", dbSingle)
    'Se establecen propiedades de validación del campo
  Campo(4).ValidationRule = "[Mayorista]>0"
  Campo(4).ValidationText = "El precio de mayorista debe ser mayor que 0"
  Set Campo(5) = NewTb.CreateField("Minorista", dbSingle)
  Set Campo(6) = NewTb.CreateField("CantidadMinima", dbInteger)
  Set Campo(7) = NewTb.CreateField()
  Campo(7).Name = "Disponible"
  Campo(7).Type = dbInteger
  Set Campo(8) = NewTb.CreateField("Proveedor", dbLong)
  Set Campo(9) = NewTb.CreateField("Fotografia", dbLongBinary)
    'Se añaden los campos a la definición de la tabla
  Dim i As Byte
  For i = 1 To 9
    NewTb.Fields.Append Campo(i)
  Next i

  'Definición de los índices de la tabla
  Dim IdxArticulo As Index, IdxMayorista As Index
  Dim CampoArticulo As Field, CampoMayorista As Field
    'Primero se crea un índice
  Set IdxArticulo = NewTb.CreateIndex("Articulo")
    'y se establece que va a ser el índice primario
  IdxArticulo.Primary = True
    'Se crea un campo que va ser el que forma el índice
  Set CampoArticulo = IdxArticulo.CreateField("Articulo")
    'y se añade el campo al índice.
  IdxArticulo.Fields.Append CampoArticulo
    'Se crea otro índice para la tabla
  Set IdxMayorista = NewTb.CreateIndex("PrecioPagado")
    'y se establece que va no va a ser de tipo único
  IdxMayorista.Unique = False
    'Si el índice es multicampo, se podrían añadir más campos
  Set CampoMayorista = IdxMayorista.CreateField("Mayorista")
    'El orden del índice va a ser descendente
  CampoMayorista.Attributes = dbDescending
  IdxMayorista.Fields.Append CampoMayorista
    'A continuación se añaden los índices a la tabla
  NewTb.Indexes.Append IdxArticulo
  NewTb.Indexes.Append IdxMayorista

  'Lo último que hay que hacer es incorporar la tabla a la base de datos
  NewDb.TableDefs.Append NewTb

    'Las tablas y los índices también se pueden crear usando consultas DDL
  Dim SQLCreate As String
  SQLCreate = "CREATE TABLE Clientes (Cliente LONG, Apellidos TEXT (30), "
  SQLCreate = SQLCreate + "Nombre TEXT (30), Direccion TEXT (40), "
  SQLCreate = SQLCreate + "Ciudad TEXT (30), Provincia TEXT (2), "
  SQLCreate = SQLCreate + "CodigoPostal TEXT (5), Interes MEMO, "
  SQLCreate = SQLCreate + "Vendedor TEXT (6))"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE TABLE Vendedores (Vendedor TEXT (6), Apellidos TEXT (30)"
  SQLCreate = SQLCreate + ", Nombre TEXT (30))"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE TABLE Pedidos (Pedido LONG, Cliente LONG, "
  SQLCreate = SQLCreate + "Vendedor TEXT (6), FechaPedido DATETIME, "
  SQLCreate = SQLCreate + "PrecioTotal SINGLE)"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE TABLE Ventas (Pedido LONG, Articulo LONG)"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE TABLE Proveedores (Proveedor LONG , Nombre TEXT (50), "
  SQLCreate = SQLCreate + "Contacto TEXT (50), Direccion TEXT (50), "
  SQLCreate = SQLCreate + "Ciudad TEXT (30), Provincia TEXT (2), "
  SQLCreate = SQLCreate + "CodigoPostal TEXT (5), Telefono TEXT (13))"
  NewDb.Execute SQLCreate

    'Creación de los índices de las tablas"
  SQLCreate = "CREATE INDEX NumCliente ON Clientes (Cliente) WITH PRIMARY"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE INDEX NumVendedor ON Vendedores (Vendedor) "
  SQLCreate = SQLCreate + "WITH PRIMARY"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE INDEX NumPedido ON Pedidos (Pedido) WITH PRIMARY"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE INDEX NumVenta ON Ventas (Pedido) WITH PRIMARY"
  NewDb.Execute SQLCreate

  SQLCreate = "CREATE INDEX NumProveedor ON Proveedores (Proveedor) "
  SQLCreate = SQLCreate + "WITH PRIMARY"
  NewDb.Execute SQLCreate

  'Definición de las relaciones entre tablas empleando el objeto relación
  Dim NewRel As Relation
  Dim CampoRel As Field
    'Aquí se crea el objeto relación
  Set NewRel = NewDb.CreateRelation("Clientes_Pedidos")
    'Se especifican las propiedades de la relación
  NewRel.Table = "Clientes"
  NewRel.ForeignTable = "Pedidos"
    'Crear el campo de relación y establecer las propiedades
  Set CampoRel = NewRel.CreateField("Cliente")
  CampoRel.ForeignName = "Cliente"
    'Agregar el campo a la relación y la relación a la DB
  NewRel.Fields.Append CampoRel
  NewDb.Relations.Append NewRel

  Set NewRel = NewDb.CreateRelation("Proveedores_Articulos")
  NewRel.Table = "Proveedores"
  NewRel.ForeignTable = "Articulos"
  Set CampoRel = NewRel.CreateField("Proveedor")
  CampoRel.ForeignName = "Proveedor"
  NewRel.Fields.Append CampoRel
  NewDb.Relations.Append NewRel

    'Se cierra la base de datos y se liberan los recursos
  NewDb.Close

  MsgBox "Base de datos creada"



    'Ahora para trabajar con la tabla debemos abrir la DB y la tabla.
  Dim WsAcuario As Workspace
  Dim DbAcuario As Database
  Dim TbClientes As Recordset
  Set WsAcuario = DBEngine.Workspaces(0)
  Set DbAcuario = WsAcuario.OpenDatabase(DbPath)
  Set TbClientes = DbAcuario.OpenRecordset("Clientes", dbOpenTable)

  On Error GoTo Errores

  WsAcuario.BeginTrans

  TbClientes.AddNew
  TbClientes("Cliente") = 1
  TbClientes("Apellidos") = "Apellido cliente 1"
  TbClientes("Nombre") = "Nombre del cliente 1"
  TbClientes("Direccion") = "Direccion cliente 1"
  TbClientes("Ciudad") = "Ciudad cliente 1"
  TbClientes("Provincia") = "Po"
  TbClientes("CodigoPostal") = "36202"
  TbClientes("Interes") = "Comentarios sobre el cliente n-mero 1"
  TbClientes("Vendedor") = "VEND1"
  TbClientes.Update

  If MsgBox("+Guardar cambios?", vbQuestion + vbYesNo, "Guardar Cambios") =
vbYes Then
    WsAcuario.CommitTrans   'Guardar los cambios
    MsgBox ("Datos Guardados")
  Else
    WsAcuario.Rollback      'No guardar los cambios
    MsgBox ("No se han guardado los datos")
  End If

  DbAcuario.Close
  Exit Sub

Errores:
  Dim Mensaje As String
  Dim Respuesta As Integer
  WsAcuario.Rollback
  Mensaje = "Error numero " & Str(Err.Number) & "  " & Err.Description
  Respuesta = MsgBox(Mensaje, vbCritical, "Error al escribir")


SQL

Instruccion   Funcion
-----------   -------
DELETE FROM   Elimina un registro de una tabla
INSERT INTO   Agrega un grupo de registros a una tabla
SELECT        Recupera un grupo de registros y los situa en una dynaset o tabla
TRANSFORM     Genera una tabla resumen utilizando el contenido de un campo como
              encabezados de columnas
UPDATE        Modifica los valores de campos especificos de la tabla

'Instruccion SELECT: Recupera un grupo de registros y los situa en una dynaset
'                    o tabla
SELECT [predicado] FieldList [INTO NombreTabla] FROM TableList
  [relaciones de tabla] [opciones de rango] [opciones de ordenacion]
  [opciones de grupo]

  'FieldList -> definición de lo campos a incluir en el recordset de salida
  '             pueden ser campos de una tabla, de varias o campos calculados
  '             basados en otros de la tabla. El formato es:
  [TableName.]Field1 [AS Alias1][, [TableName.]Field2 [AS Alias2]]...
  '             el * se puede usar para seleccionar todos los campos de la
  '             tabla especificada.
  '             Lo campos calculados se pueden obtener a partir de operaciones
  '             aritmeticas (+, -, *, /, ^) con campos numericos o mediante la
  '             union de campos alfanumericos (operador &). Tambien  se pueden
  '             usar funciones propias de Visual Basic.
  '             Mediante el uso de la clausula AS, se puede especificar un
  '             nombre alternativo para el campo.
  '             Tambien se puede usar SELECT para realizar calculos sobre la
  '             informacion de la tabla, mediante las funciones de agregado de
  '             SQL. Estas funciones de agregado devuelven un solo valor para
  '             todo el conjunto de registros, a menos que se emplee la clausula
  '             GROUP BY que devuelve un valor para grupo de registros. Las
  '             funciones de agregado disponibles son:
  '             AVG: Media aritmetica del campo
  '             COUNT: Numero de registros
  '             MIN: Valor minimo del campo
  '             MAX: Valor maximo del campo
  '             SUM: Valor total del campo (suma de todos los valores)
  '             FIRST: Valor del campo para el primer registro del recordset
  '             LAST: Valor del campo para el ultimo registro del recordset
  '             STDEV: Desviacion tipica de los valores del campo
  '             STDEVP: Desviacion tipica de los valores del campo
  '             siempre referidas a los registros que cumplan la cláusula WHERE

  'TableList -> Se usa para indicar la o las tablas de donde se va a coger la
  '             informacion. El formato es:
  FROM Tabla1 [IN DataBase1] [AS Alias1][, Tabla2 [IN DataBase2] [AS Alias2]]...
  '             La parte IN de la clausula se usa para especificar la base de
  '             datos donde esta la tabla.
  '             Usando la parte AS de la clausula se puede asignar un alias
  '             la tabla para usarlo en el resto de las clausulas

  'predicado -> Se usa para especificar si se desan todos los registros que
  '             cumplan las condiciones o determinar valores únicos para
  '             los campos. El formato es:
  SELECT [{ALL/DISTINCT/DISTINCTROW}] FieldList
  '             Usando el predicado ALL, que se coge por defecto, se seleccionan
  '             todos los registros para la consulta. Con DISTINCT el motor de
  '             DB recupera solo un registro con un conjunto especificado de
  '             valores de campo (independientemente de cuantos duplicados
  '             haya); o sea, para que un registro sea rechazado debe de tener
  '             los valores de todos los campos seleccionados iguales a los de
  '             otro registro. El predicado DISTINCTROW compara los valores de
  '             todos los campos de la tabla, esten o no seleccionados.

  'relaciones de tabla -> Se usa para poder especificar las relaciones entre
  '             las diferentes tablas que configuran la consulta. Existen dos
  '             formas de especificar las relaciones: JOIN y WHERE. Mediante el
  '             uso de WHERE se genera un recordset de solo lectura.
  '             JOIN: Combina dos tablas en base al contenido de campos
  '             especificos de cada una y el tipo de JOIN. Su formato es:
  Tabla1 {INNER|LEFT|RIGHT} JOIN Tabla2 ON Tabla1.Clave1 = Tabla2.Clave2
  '             Al usar INNER, de ambas tablas solo se cogen aquellos registros
  '             que tengan correspondecia con la otra tabla. Mediante LEFT, de
  '             la tabla de la izquierda se cogen todos los registros y de la
  '             tabla de la derecha solo los que tengan correspondecia en la
  '             tabla de la izquierda. Con RIGHT se consigue el caso contrario.
  '             WHERE: Se usa para filtrar los registros devueltos por una
  '             consulta, pero se puede emplear para emular una INNER JOIN
  WHERE [Tabla1].Field1 = [Tabla2].Field2
  '             La clausula WHERE funciona igual que INNER JOIN. El recodset
  '             obtenido es de solo lectura

  'opciones de rango -> Se usa para especificar el rango de los registros a
  '             procesar. El formato es:
  WHERE ExpresionLogica1 [{AND|OR} ExpresionLogica2]...
  '             Existen cuatro tipos de predicados (de expresiones logicas) que
  '             se pueden usar con la clausula WHERE:
  '             Predicado de comparacion: Compara un campo con un valor dado.
  '             Los operadores que se pueden usar son < <= = >= > <>
  Expresion1 Comparador Expresion2
  '             Predicado LIKE: Compara un campo con un modelo. Los patrones
  '             se pueden hacer con * (equivale a multiples caracteres), ? (un
  '             caracter), # (un digito), [lista] (un caracter de la lista; por
  '             ejemplo, [c-f] para c, d, e y f), [!lista] (para un caracter
  '             que no este en la lista), o una combinacion de los anteriores.
  Expresion LIKE Modelo
  '             Predicado IN: Compara un campo con una lista de valores
  '             aceptables.
  Expresion IN Lista
  '             Predicado BETWEEN: Compara un campo con un rango de valores. La
  '             busqueda es inclusiva, o sea, si el valor es igual a uno de los
  '             puntos finales del intervalo, se incluye el registro
  Expresion [NOT] BETWEEN Valor1 AND Valor2

  'opciones de ordenacion -> Se usa para determinar el orden en que han de
  '             aparecer los registros en la dynaset de salida.
  ORDER BY Field1 [ASC|DESC][, Field2 [ASC|DESC][, ...]]
  '             Empleando la palabra clave ASC se especifica que la ordenacion
  '             va a ser ascendente, mientras que con DESC la ordenacion sera
  '             descendente (por defecto se toma ascendente)

  'opciones de grupo -> Permite generar un recordset que solamente tiene un
  '             registro por caso de unos campos especificados. Su formato es:
  GROUP BY Field1 [, Field2]... [HAVING ExpLogica1 [{AND|OR} ExpLogica2]...]
  '             Esta clausula indica que se han de agrupar las filas de la
  '             tabla, de tal manera que todas las que tengan iguales valores
  '             en las columnas de agrupamiento formen un grupo.
  '             Mediante la clausula HAVING se puede especificar cuales de los
  '             registros seleccionados (mediante WHERE) hay que visualizar.

  'NombreTabla -> permite especificar el nombre de una tabla donde se grabara
  '             la consulta obtenida. Su sintaxis es:
  INTO NombreTabla
  '             La instruccion SELECT genera un synaset o un snapshot temporal,
  '             esto es, su contenido unicamente existe mientras esten abiertos.
  '             Mediante el uso de la clausula INTO se especifica un nombre de
  '             una tabla y la consulta se guardará permanentemente en esa
  '             tabla (si ya existia, la salida la reescribe)


'Instruccion DELETE: Elimina un registro (o varios) de una tabla
DELETE FROM NombreTabla [WHERE ClausulaWhere]
  'clausula WHERE -> Se usa para especificar un criterio a cumplir por los
  '             registros a borrar. En esta clausula se puede emplear cualquier
  '             predicado de comparacion. Si se omite esta clausula, se borran
  '             todos los registros de la tabla


'Instruccion INSERT INTO: Agrega un grupo de registros a una tabla
INSERT INTO NombreTabla [IN DataBase] [(Field1[, Field2]...)]
  { SELECT InstruccionSelect | VALUES (Value1[, Value2]...) }
  'Field1, Field2,... -> Lista de nombres de columnas de la tabla que van a
  '             recibir los valores enviados. No hace falta poner todas de las
  '             que consta la tabla ni ponerlas en el mismo orden en que han
  '             sido definidos. Si se omite, se interpreta como si se
  '             especificara una lista incluyendolas a todas y en dicho orden.
  'instruccion SELECT -> Si es emplea, los datos a añadir a la tabla seran los
  '             que devuelva la consulta SELECT.
  'clausula VALUES -> Si se emplea, se crea un registro en la tabla con los
  '             valores especificados con esta clausula.


'Instrucción UPDATE: Modifica los valores de campos especificos de la tabla
UPDATE NombreTabla SET Field1=Valor1[, Field2=Valor2]...  [WHERE ClausulaWhere]
  'clausula SET -> Especifica los campos a modificar y los nuevos valores.
  'clausula WHERE -> Se usa para especificar un criterio a cumplir por los
  '             registros a modificar. En esta clausula se puede emplear
  '             cualquier predicado de comparacion. Si se omite esta clausula,
  '             se modifican todos los registros de la tabla


'Ejecución de instrucciones SQL desde VB:
DateBase.EXECUTE Source[, Options]
  ' Ejecuta la instrucción SQL en la base de datos indicada. Solo admite las
  '             instrucciones que son de acción, no las de consulta que
  '             devuelven un recordset
  'Source -> Instruccion SQL a ejecutar
  'Options -> Integer que determina las caracteristicas de integridad de datos
  '             de la consulta. Puede tener una combinacion de los siguientes
  '             valores:
  '     dbDenyWrite       Deny write permission to other users.
  '     dbInconsistent    (Default) Inconsistent updates.
  '     dbConsistent      Consistent updates.
  '     dbSQLPassThrough  SQL pass-through. Causes the SQL statement to be
  '                       passed to an ODBC database for processing.
  '     dbFailOnError     Roll back updates if an error occurs.
  '     dbSeeChanges      Generate a run-time error if another user is changing
  '                       data you are editing
Set Querydef = DataBase.CreateQueryDef([Name][, Source]
Querydef.EXECUTE [Options]
  ' Permite crear una consulta o una acción SQL en la base de datos para despues
  '             ejecutarla. Esta instruccion SQL se almacen en la base de datos
  '             junto con las tablas
  'Name -> Nombre que tendra la consulta SQL en la base de datos
  'Source -> Instruccion SQL a ejecutar
  'Options -> Las mismas que para DataBase.EXECUTE


Ejemplos de SQL

' En la sintaxis SQL se debe de usar comillas simples en vez de dobles.

  'Seleccionar todos los registros de una tabla con todos sus campos
SELECT *
      FROM Ventas
  'Seleccionar todos los registros, pero solo unos campos
  ' los nombres de campos con espacios en blanco deben ir entre corchetes.
SELECT Articulo, Descripcion, [Precio Venta]
      FROM Ventas
  'Seleccionar todos los campos de la tabla Ventas y los campos Descripcion
  ' y Minorista de la tabla de Articulos, relacionando ambas tablas por el
  ' codigo del articulo.
SELECT Ventas.*, Articulos.Descripcion, Articulos.Minorista
      FROM Ventas, Articulos
      WHERE Ventas.Articulo = Articulos.Articulo
  'Calcular el precio total de los articulos. Esta consulta crea un campo
  ' con el resultado de la multiplicacion
SELECT Articulos.Minorista * Ventas.Cantidad
      FROM Articulos, Ventas
      WHERE Ventas.Articulo = Articulos.Articulo
  'Crea una consulta con el apellido y el nombre de los clientes, separados
  ' por una coma, en un solo campo
SELECT Apellido & ", " & Nombre
      FROM Clientes
  'Crea un identificador de cliente utilizando las 3 primeras letras de los
  ' campos Apellidos y Nombre y pone todo en mayusculas
SELECT UCASE$(MID$(Apellidos, 1, 3) & UCASE$(MID$(Nombre, 1, 3)
      FROM Clientes
  'Crea un recordset con un único registro con el stock mínimo, el máximo
  ' y el medio de los artículos así como el coste total de las existencias
SELECT Min(Stock), Max(Stock), Avg(Stock), Sum(Stock * Articulos.Precio)
      FROM Articulos
  'Crea una consulta compuesta de dos campos, una cantidas y la raiz cuadrada
  ' de esa cantidad. A estos campos les asigna un nombre alternativo
SELECT Cantidad AS Cant1, SQR(Cantidad) AS Cant2
      FROM Ventas
  'Crea una consulta con datos de dos bases de datos diferentes
SELECT Clientes.Apellido & Clientes.Nombre AS Nombre, [Codigos
Postales].Ciudad,
       [Codigos Postales].Provincia
      FROM Clientes, [Codigos Postales] IN Codigos
      WHERE Clientes.[Codigo Postal] = [Codigos Postales].[Codigo Postal]
  'Lo mismo que el anterior ejemplo, pero usando un alias para las tablas
SELECT CS.Apellido & CS.Nombre AS Nombre, CP.Ciudad, CP.Provincia
      FROM CS, CP IN Codigos
      WHERE CS.[Codigo Postal] = CP.[Codigo Postal]
  'No se seleccionan los registros que tengas todos los campos en ambas tablas
  ' iguales
SELECT DISTINCTROW Articulo
      FROM Articulos, Ventas
      WHERE Articulos.Articulo = Ventas.Articulo
  'Se genera un recordset con todos los registros de la tabla Clientes, exista
  ' o no el vendedor asociado, en la que no saldrán reflejados los vendedores
  ' que no tienen ningún cliente asignado
SELECT CS.Apellido, CS.Nombre, VN.Apellido, VN.Nombre
      FROM Clientes AS CS, Vendedores AS VN
      CS LEFT JOIN VN ON CS.Vendedor = VN.Vendedor
  'Selecciona todos los campos de los clientes que se apelliden Perez
SELECT *
      FROM Clientes
      WHERE Apellido = "Perez"
  'Selecciona todos los campos de los artículos con fecha mayor que 15/12/96
SELECT *
      FROM Articulos
      WHERE Fecha > #15/12/96#
  'Selecciona todos los campos de los clientes que tengan como segunda letra
  ' del apellido, una letra a, b o c
SELECT *
      FROM Clientes
      WHERE MID$(Apellido, 2, 1) LIKE "[a-c]"
  'Selecciona todos los campos de los clientes que tengan un apellido que no
  ' empieze por una vocal y que la tercera letra sea una n
SELECT *
      FROM Clientes
      WHERE LCASE$(Apellido) = "[!aeiou]?n*"
  'Selecciona todos los campos de los clientes que sean gallegos
SELECT *
      FROM Clientes
      WHERE Provincia IN ("C", "Lu", "Or", "Po")
  'Selecciona los clientes con fecha de enero de 1997
SELECT *
      FROM Clientes
      WHERE Fecha BETWEEN #1/01/97# AND #31/01/97#
  'Selecciona los clientes con apellidos que no estén entre la M y la P
SELECT *
      FROM Clientes
      WHERE Apellido NOT BETWEEN "M" AND "P"
  'Selecciona los clientes que se apelliden Martinez de Pontevedra y Orense
SELECT *
      FROM Clientes
      WHERE Apellido = "Martinez" AND Provincia IN ("Po","OR")
  'Selecciona los clientes ordenandolos por apellido (de forma descendente) y
  ' por el nombre (de forma ascendente)
SELECT *
      FROM Clientes
      ORDER BY Apellido DESC, Nombre
  'Obtiene el total de ventas de las provincias
SELECT Provincia, SUM(VentasTotales)
      FROM Clientes
      GROUP BY Provincia
  'Obtiene el total de ventas de las provincias que tengan mas de 10 clientes
  ' y la venta maxima a un solo cliente no sea superior a 1000
SELECT Provincia, SUM(VentasTotales)
      FROM Clientes
      GROUP BY Provincia
      HAVING COUNT(*) > 10 AND MAX(VentasTotales) < 1000
  'Obtiene una nueva tabla, Correos, con las direcciones de los clientes
SELECT CS.Apellido & ", " & CS.Nombre AS Nombre, CS.Direccion,
      CP.Ciudad, CP.Provincia, CS.[Codigo Postal]
      INTO Correos
      FROM Clientes AS CS, [Codigo Postal] IN Codigos AS CP
      WHERE CS.[Codigo Postal] = CP.[Codigo Postal]


  'Elimina todos los clientes que vivan en Sevilla
DELETE FROM Clientes WHERE Provincia = "Se"


  'Actualiza (añade nuevos registros) la tabla de direcciones de corro creada
  ' con la consulta SELECT INTO de mas arriba.
INSERT INTO  Correo
      SELECT CS.Apellido & ", " & CS.Nombre, CS.Direccion,
      CP.Ciudad, CP.Provincia, CS.[Codigo Postal]
      FROM Clientes AS CS, [Codigo Postal] IN Codigos AS CP
      WHERE CS.[Codigo Postal] = CP.[Codigo Postal] AND CS.Fecha > UltimoMes
  'Añade un nuevo registro a la tabla de correo
INSERT INTO  Correo
      VALUES ("Perez, Jose", "Calle Mayor", "Vigo", "Po", "36201")


  'Modifica el identificador de vendedor para todos los clientes que tengan
  ' el vendedor Perez.
UPDATE Clientes
      SET Vendedor="GUTI"
      WHERE Vendedor="PEREZ"
  'Aumenta el precio al por menor de todos los articulos en un 5%
UPDATE Articulos
      SET Minorista=Minorista*1.05


  'Ejecuta una consulta SQL
DIM Db as Database
DIM Qd as QueryDef
Dim SQL as String
SQL = "DELETE FROM Titles WHERE ISBN IS NULL"
  ' mediante el uso de ejecutar de la base de datos
Db.EXECUTE SQL, dbFailOnError
  ' mediante la creacion de una QueryDef
Set Qd = Db.CreateQueryDef("Borrar libros sin ISBN", SQL)
Qd.EXECUTE dbFailOnError
  ' ejecutar la consulta con el método ejecutar base de datos
Db.EXECUTE "Borrar libros sin ISBN", dbFailOnError

ir al índice