zoukankan      html  css  js  c++  java
  • 数据库的高级设计

    一.标准化

    数据库的设计中,最小化数据冗余和数据库的效率之间存在一个折衷。

    1.第一范式:

    • 定义所需要的数据项,将相关的数据项放置在一个表中。
    • 确保没有重复的数据组。(可以通过将数据划分到多个表中,来删除重复的数据)
    • 确保存在一个主键。

    主键:记录的唯一标示符。可以添加一个新列,或者使用现有的一个或者多个列,只要这些列能够组合成一个唯一的主键。

    2.第二范式:要求主键中的任意列没有局部相关性。

    3.第三范式(可选项,依赖于环境):符合第二范式,所有非主键字段都依赖主键。

    传递相关性。消除传递相关性——把具有传递相关性的数据项单独放在一个表中。

    好处是:数据重复量降低;数据完整性,避免重复数据改变时,只更新了某些数据的危险。

    不利因素:增加了复杂性并且降低了效率。

    二.利用约束确保数据的有效性

     1.NOT NULL约束

    Create table mytable(Column1 int not null, Column2 varchar(20));
    alter table mytable
    alter column column2 varchar(20) not null ;   --将一列更改为not null类型。这个更改能够成功的前提是,原数据表中没有null型的记录。对于其他的约束修改也是一样的,不能够和表中的已有数据冲突。

    2.UNIQUE约束

     --一种添加unique约束的方式
    Create table mytable(Column1 int not null unique, Column2 varchar(20) unique);  
    
    --另一种添加unique约束的方式,在定义的列列举之后添加约束,可以为约束指定一个名称,并且可以使用SQL语句删除该约束.
    --可以指定两个或者多个列的组合必须为唯一
    Create table anothertable(
      Column1 int,
      Column2 varchar(20),
      Column3 varchar(12),
      CONSTRAINT MyUniqueConstraint UNIQUE(Column1,Column2),
      CONSTRAINT AnotherUniqueConstraint UNIQUE(Column1,Column3)  
      )  ;
    Alter table anothertable
    drop constraint MyUniqueConstraint;
    Alter table anothertable
    add CONSTRAINT MyUniqueConstraint UNIQUE(Column1,Column2);

    3.CHECK约束

    CREATE TABLE NamesAges(
       Name varchar(50),
       Age int CHECK(Age>=0)    --Age列的条件必须为true或者unknown
    );
    
    INSERT INTO NamesAges(Name,Age) Values('JIM',30);    --成功
    INSERT INTO NamesAges(Name) Values('JIM');     --成功
    INSERT INTO NamesAges(Name,Age) Values('JIM',-22);  --失败
    
    delete from NamesAges where Age is null;  
    Alter table NamesAges
    alter column Age int not null;   
    
    alter table NamesAges
    add constraint Age check(age<=40);  --另一种方法添加check约束
    CREATE TABLE Employee
    (
          EmployeeName varchar(50),
          AvgMonthlyWage decimal(12,2),
          HourlyRate decimal(12,2),
          CONSTRAINT hourlyLess CHECK(AvgMonthlyWage>HourlyRate),  --如果希望CHECK条件子句包含表中的多个列,则需要在列末尾定义它
    )
    
    --或者使用alter table和add constraint
    alter table Employee
    add constraint hourlyLess CHECK(AvgMonthlyWage>HourlyRate);

    4.主键和PRIMARY KEY约束

    --主键提供了表之间的链接
    --主键约束是UNIQUE和NOT NULL的组合
    create table HolidayBookings
    (
      CustomerId int primary key,  
      BookingId int NOT NULL,
      Destination varchar(50),
    )
    
    --组合主键
    create table MoreHolidayBookings
    (
      CustomerId int NOT NULL,  
      BookingId int NOT NULL,
      Destination varchar(50),
      CONSTRAINT booking_pk PRIMARY KEY(CustomerId,BookingId)  --同一个人不能同时借两本相同的数。一个人可以借多本书,相同的书号的数也可以被多人借。主键约束,不允许CustomerId,BookingId中的任何一个为null
    );
    
    --为现有表添加主键约束,前提条件是被设为主键的列已经被定义成了not null型
    create table MoreHolidayBookings
    (
      CustomerId int NOT NULL,  
      BookingId int NOT NULL,
      Destination varchar(50),
    );
    alter table MoreHolidayBookings
    add constraint more_holiday_pk primary kay(CustomerId,BookingId) 

     5.外键约束

    外键是访问另一个表的主键的列。

    假设有2个表Location和Attenedance,在利用内部联接来查找数据时,查找Attenedance.LocationId=Location.LocationId的数据。当往Attenedance中插入了一个记录,其Attenedance.LocationId值在Location中无效的时候,破坏了这种联接性。

    外键约束就可以保证这种联接性,即一个表中的一个列是引用另一个表中的记录行的方法。

    alter table attendance add constraint location_fk foreign key(LocationId) references Location(LocationId);   --由一列组成的主键和外键
    --当创建了外键约束后,如果往attendance中添加的记录,其LocationId在它所依赖的主键中无效,那么添加会出错
    
    alter table SomeTable ADD CONSTRAINT sometable_fkl foreign key (employeename,employeeid,membershipid) references someprimarykeytable(employeename,employeeid,membershipid);  --主键和外键由3列组成
    
    --也可以在创建一个表的时候就添加主键
    create table attendence
    (
         LocationId integer,
         MeetingDate date,
         MemberAttended char(1),
         MemberId integer,
         CONSTRAINT SomeTable_fk1 FOREIGN KEY (LocationId) REFERENCES Location(LocationId)
    );

    三.利用索引加速结果查询

    CREATE INDEX index_name ON table_name (col1,col2);  --创建索引
    select col1,col2 from table_name;    --添加了索引后,输出结果按升序排列。默认情况下,索引按升序排列。
    DROP INDEX table_name.index_name;    --删除索引
    select col1,col2 from table_name;     --删除索引后,输出结果不再按照顺序排列
    create unique index index_name on table_name(col1 desc,col2);   --创建一个唯一的索引,按col1的降序排列然后按col2的升序排列
  • 相关阅读:
    Why to define my own blog skin
    安装drupal7.7
    同步和异步的区别
    神马是云计算神马是物联网
    zen主题安装图文记录
    《那些年啊,那些事——一个程序员的奋斗史》——127
    《一个程序员的奋斗史》帮我选封面哇! —— 猜封面页数赢赠书活动~
    《那些年啊,那些事——一个程序员的奋斗史》——126
    《那些年啊,那些事——一个程序员的奋斗史》——128 (终章)
    伍定轩乱语
  • 原文地址:https://www.cnblogs.com/wy1290939507/p/4506677.html
Copyright © 2011-2022 走看看