主键 外键

news2025/2/23 12:40:16

主键 外键

在这里插入图片描述

在关系型数据库中,主键(Primary Key)和外键(Foreign Key)是用于维护数据完整性和建立表之间关系的重要概念。

主键(Primary Key)

  • 定义: 主键是一个或多个列的组合,其值能够唯一标识表中的每一行。
  • 特性:
    • 唯一性: 主键的值必须是唯一的,不能重复。
    • 非空性: 主键列不能包含 NULL 值。
    • 单一性: 每个表只能有一个主键。
  • 用途: 主键用于确保每一行数据的唯一性,并作为其他表引用的基础。
示例

假设有一个 users 表:

CREATE TABLE users (
    user_id INT PRIMARY KEY,
    username VARCHAR(50),
    email VARCHAR(100)
);

在这个例子中,user_id 是主键,它唯一标识每个用户。

外键(Foreign Key)

  • 定义: 外键是一个或多个列的组合,其值引用另一个表中的主键。
  • 特性:
    • 引用完整性: 外键值必须在被引用的表中存在(或为 NULL)。
    • 多对一关系: 外键通常用于建立表之间的多对一关系。
  • 用途: 外键用于维护表之间的关系和引用完整性。
示例

假设有一个 orders 表,其中 user_id 是外键,引用 users 表的主键:

CREATE TABLE orders (
    order_id INT PRIMARY KEY,
    order_date DATE,
    user_id INT,
    FOREIGN KEY (user_id) REFERENCES users(user_id)
);

在这个例子中,user_id 是外键,它引用 users 表中的 user_id 主键。这确保了每个订单都与一个有效的用户相关联。

主键和外键的关系

  • 主键: 定义在一个表中,用于唯一标识该表中的记录。
  • 外键: 定义在一个表中,用于引用另一个表的主键,从而建立两个表之间的关系。

维护数据完整性

  • 级联操作: 可以设置外键约束的级联操作,如 ON DELETE CASCADE,以便在删除或更新主表记录时自动更新或删除相关的外键记录。
  • 约束检查: 数据库在插入或更新数据时会检查外键约束,以确保引用完整性。

通过使用主键和外键,你可以确保数据库中的数据完整性,并建立表之间的关系,从而更好地组织和管理数据。

主键 外键 mybatis

在使用 MyBatis 进行数据库操作时,主键和外键的概念依然适用,因为它们是数据库层面的约束和关系。MyBatis 是一个持久层框架,它通过 XML 或注解的方式将 SQL 语句与 Java 对象进行映射。以下是如何在 MyBatis 中处理主键和外键的基本方法:

主键处理

  1. 自动生成主键

    在数据库中,主键通常是自动生成的(例如,自增 ID)。在 MyBatis 中,可以使用 useGeneratedKeyskeyProperty 来获取自动生成的主键值。

    <insert id="insertUser" parameterType="User" useGeneratedKeys="true" keyProperty="userId">
        INSERT INTO users (username, email) VALUES (#{username}, #{email})
    </insert>
    
    • useGeneratedKeys="true": 告诉 MyBatis 使用数据库生成的主键。
    • keyProperty="userId": 指定实体类中用于存储生成主键的属性。
  2. 手动设置主键

    如果主键不是自动生成的,你需要在插入数据时手动设置主键值。

    <insert id="insertUser" parameterType="User">
        INSERT INTO users (user_id, username, email) VALUES (#{userId}, #{username}, #{email})
    </insert>
    

外键处理

外键关系通常在数据库设计时定义。在 MyBatis 中,处理外键关系主要涉及到如何查询和映射相关联的数据。

  1. 一对多关系

    假设一个用户可以有多个订单,你可以在 MyBatis 中定义一个查询来获取用户及其订单列表。

    <select id="selectUserWithOrders" resultMap="UserOrderMap">
        SELECT u.user_id, u.username, o.order_id, o.order_date
        FROM users u
        LEFT JOIN orders o ON u.user_id = o.user_id
        WHERE u.user_id = #{userId}
    </select>
    
    <resultMap id="UserOrderMap" type="User">
        <id property="userId" column="user_id"/>
        <result property="username" column="username"/>
        <collection property="orders" ofType="Order">
            <id property="orderId" column="order_id"/>
            <result property="orderDate" column="order_date"/>
        </collection>
    </resultMap>
    
    • resultMap: 定义如何将查询结果映射到 Java 对象。
    • collection: 用于映射一对多关系,将多个订单映射到一个用户对象的 orders 属性。
  2. 多对一关系

    如果一个订单属于一个用户,你可以在订单查询中包含用户信息。

    <select id="selectOrderWithUser" resultMap="OrderUserMap">
        SELECT o.order_id, o.order_date, u.user_id, u.username
        FROM orders o
        JOIN users u ON o.user_id = u.user_id
        WHERE o.order_id = #{orderId}
    </select>
    
    <resultMap id="OrderUserMap" type="Order">
        <id property="orderId" column="order_id"/>
        <result property="orderDate" column="order_date"/>
        <association property="user" javaType="User">
            <id property="userId" column="user_id"/>
            <result property="username" column="username"/>
        </association>
    </resultMap>
    
    • association: 用于映射多对一关系,将用户信息映射到订单对象的 user 属性。

总结

  • 主键: 在 MyBatis 中,可以通过 useGeneratedKeyskeyProperty 来处理自动生成的主键。
  • 外键: 通过 resultMapcollectionassociation 来处理表之间的关系和数据映射。

通过这些配置,你可以在 MyBatis 中有效地处理主键和外键关系,确保数据的完整性和一致性。

主键 外键 hibernate

在 Hibernate 中,主键和外键的概念同样适用,因为它们是关系型数据库的基本组成部分。Hibernate 是一个对象关系映射(ORM)框架,它将 Java 对象映射到数据库表中。以下是如何在 Hibernate 中处理主键和外键的基本方法:

主键处理

  1. 简单主键

    在 Hibernate 中,简单主键通常使用 @Id 注解来标识。可以结合 @GeneratedValue 注解来自动生成主键值。

    import javax.persistence.Entity;
    import javax.persistence.GeneratedValue;
    import javax.persistence.GenerationType;
    import javax.persistence.Id;
    
    @Entity
    public class User {
        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        private Long userId;
    
        private String username;
        private String email;
    
        // Getters and setters
    }
    
    • @Id: 标识主键字段。
    • @GeneratedValue: 指定主键生成策略。GenerationType.IDENTITY 通常用于自增主键。
  2. 复合主键

    对于复合主键,可以使用 @EmbeddedId@IdClass 注解。

    import javax.persistence.Embeddable;
    import java.io.Serializable;
    
    @Embeddable
    public class OrderId implements Serializable {
        private Long orderId;
        private Long userId;
    
        // Getters, setters, equals, and hashCode
    }
    
    import javax.persistence.EmbeddedId;
    import javax.persistence.Entity;
    
    @Entity
    public class Order {
        @EmbeddedId
        private OrderId id;
    
        private String orderDate;
    
        // Getters and setters
    }
    
    • @Embeddable: 用于定义复合主键类。
    • @EmbeddedId: 用于在实体中嵌入复合主键。

外键处理

外键用于定义实体之间的关系。在 Hibernate 中,使用 @ManyToOne, @OneToMany, @OneToOne, 和 @ManyToMany 注解来定义这些关系。

  1. 多对一关系

    在订单和用户之间的多对一关系中,订单表中的 userId 是外键。

    import javax.persistence.Entity;
    import javax.persistence.GeneratedValue;
    import javax.persistence.GenerationType;
    import javax.persistence.Id;
    import javax.persistence.ManyToOne;
    
    @Entity
    public class Order {
        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        private Long orderId;
    
        private String orderDate;
    
        @ManyToOne
        private User user;
    
        // Getters and setters
    }
    
    • @ManyToOne: 定义多对一关系,通常在外键字段上使用。
  2. 一对多关系

    在用户和订单之间的一对多关系中,用户表中的 userId 是主键,订单表中的 userId 是外键。

    import javax.persistence.Entity;
    import javax.persistence.GeneratedValue;
    import javax.persistence.GenerationType;
    import javax.persistence.Id;
    import javax.persistence.OneToMany;
    import java.util.List;
    
    @Entity
    public class User {
        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        private Long userId;
    
        private String username;
        private String email;
    
        @OneToMany(mappedBy = "user")
        private List<Order> orders;
    
        // Getters and setters
    }
    
    • @OneToMany: 定义一对多关系,mappedBy 属性指定关系的拥有方。
  3. 一对一关系

    使用 @OneToOne 注解来定义一对一关系。

    import javax.persistence.Entity;
    import javax.persistence.GeneratedValue;
    import javax.persistence.GenerationType;
    import javax.persistence.Id;
    import javax.persistence.OneToOne;
    
    @Entity
    public class UserProfile {
        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        private Long profileId;
    
        private String address;
    
        @OneToOne
        private User user;
    
        // Getters and setters
    }
    
    • @OneToOne: 定义一对一关系。

总结

  • 主键: 使用 @Id@GeneratedValue 来定义和生成主键。
  • 外键: 使用关系注解(如 @ManyToOne, @OneToMany)来定义实体之间的关系。

通过这些注解和配置,你可以在 Hibernate 中有效地处理主键和外键关系,确保数据的完整性和一致性。

主键 外键 mybatis plus

MyBatis-Plus 是 MyBatis 的增强版,提供了许多便捷的功能来简化开发过程。在 MyBatis-Plus 中,主键和外键的处理与 MyBatis 类似,但它提供了一些额外的工具和注解来简化这些操作。

主键处理

  1. 自动生成主键

    MyBatis-Plus 支持自动生成主键,通常通过数据库的自增字段实现。你可以使用 @TableId 注解来指定主键字段,并设置主键生成策略。

    import com.baomidou.mybatisplus.annotation.IdType;
    import com.baomidou.mybatisplus.annotation.TableId;
    import com.baomidou.mybatisplus.annotation.TableName;
    
    @TableName("users")
    public class User {
        @TableId(value = "user_id", type = IdType.AUTO)
        private Long userId;
    
        private String username;
        private String email;
    
        // Getters and setters
    }
    
    • @TableId: 用于标识主键字段。
    • IdType.AUTO: 指定主键生成策略为自增。
  2. 手动设置主键

    如果主键不是自动生成的,你可以在插入数据时手动设置主键值。

    @TableId(value = "user_id", type = IdType.INPUT)
    private Long userId;
    
    • IdType.INPUT: 指定主键由用户输入。

外键处理

外键关系通常在数据库设计时定义。在 MyBatis-Plus 中,处理外键关系主要涉及到如何查询和映射相关联的数据。MyBatis-Plus 本身不直接处理外键关系,但你可以通过编写 SQL 查询和使用关联查询来实现。

  1. 一对多关系

    假设一个用户可以有多个订单,你可以在 MyBatis-Plus 中定义一个查询来获取用户及其订单列表。

    @TableName("orders")
    public class Order {
        @TableId(value = "order_id", type = IdType.AUTO)
        private Long orderId;
    
        private String orderDate;
        private Long userId;
    
        // Getters and setters
    }
    

    你可以使用自定义 SQL 查询来获取用户及其订单:

    @Select("SELECT u.user_id, u.username, o.order_id, o.order_date FROM users u LEFT JOIN orders o ON u.user_id = o.user_id WHERE u.user_id = #{userId}")
    List<UserWithOrders> selectUserWithOrders(@Param("userId") Long userId);
    
  2. 多对一关系

    如果一个订单属于一个用户,你可以在订单查询中包含用户信息。

    @Select("SELECT o.order_id, o.order_date, u.user_id, u.username FROM orders o JOIN users u ON o.user_id = u.user_id WHERE o.order_id = #{orderId}")
    OrderWithUser selectOrderWithUser(@Param("orderId") Long orderId);
    

总结

  • 主键: 使用 @TableId 注解来定义主键字段,并指定主键生成策略。
  • 外键: 通过自定义 SQL 查询和关联查询来处理表之间的关系。

MyBatis-Plus 提供了许多便捷的功能来简化数据库操作,但对于复杂的外键关系,仍然需要通过 SQL 查询来实现。通过这些配置和查询,你可以在 MyBatis-Plus 中有效地处理主键和外键关系,确保数据的完整性和一致性。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2217382.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【从零开发Mybatis】引入MapperConfig.xml和Mapper映射配置

引言 学习MyBatis源码之前&#xff0c;了解它是如何通过JDBC查询数据库数据的基础知识是非常有用的。 上一篇我们编写了一个最简单的示例&#xff0c;通过JDBC查询数据库数据&#xff0c;从本文开始&#xff0c;我们将正式开始Mybatis框架的开发。 通过JDBC查询数据库数据存…

计算机网络:数据链路层 —— 共享式以太网

文章目录 共享式以太网CSMA/CD 协议CSMA/CD 协议 的基本原理 共享式以太网的争用期共享式以太网的最小帧长共享式以太网的最大帧长共享式以太网的退避算法截断二进制指数退避算法 共享二进制以太网的信道利用率使用集线器的共享式以太网10BASE-T 共享式以太网 共享式以太网是当…

微分几何-曲线论(曲线)

文章目录 曲线定义常见曲线直线圆圆柱螺线维维安尼曲线 连续曲线/光滑曲线正则曲线切向量切线方程法平面&#xff08;法面&#xff09; 弧长定理1&#xff1a;弧长公式弧长参数化定理2&#xff1a;任何一条正则曲线都可以使用弧长作参数.&#xff08;也称弧长参数为**自然参数*…

[Linux] 逐层深入理解文件系统 (1)—— 进程操作文件

标题&#xff1a;[Linux] 文件系统 &#xff08;1&#xff09;—— 进程操作文件 个人主页水墨不写bug &#xff08;图片来源于网络&#xff09; 目录 一、进程与打开的文件 二、文件的系统调用与库函数的关系 1.系统调用open() 三、内存中的文件描述符表 四、缓冲区…

【Java SE 】类和对象详解

&#x1f525;博客主页&#x1f525;&#xff1a;【 坊钰_CSDN博客 】 欢迎各位点赞&#x1f44d;评论✍收藏⭐ 目录 1&#xff0c; 面向对象认识 1.1 什么时面向对象 1.2 面向对象和面向过程 1.2.1 一个例子理解对象和过程 1. 对于电脑来说 2. 对于我们人来说 2. 类的定…

还在为调用大模型API接口返回数据的处理问题烦恼???来看看这篇文章,解决你的烦恼!!!

大家好&#xff01;我是学徒小z&#xff0c;今天给大家分享一下我做项目过程中遇到的一个问题。 文章目录 问题大模型接口解决方案流式返回和回调函数另一个问题1. 使用web组件2. 使用第三方库 问题 不知道大家有没有遇到这样一个问题。在调用大模型接口的时&#xff0c;返回…

Lnmp(mysql分离)(nginx 1.13.6+mysql5.5+php5.3)环境一键搭建

Lnmp&#xff08;mysql分离&#xff09;&#xff08;nginx 1.13.6mysql5.5php5.3&#xff09;环境一键搭建 如果对运维课程感兴趣&#xff0c;可以在b站上、csdn或微信视频号 上搜索我的账号&#xff1a; 运维实战课程&#xff0c;可以关注我&#xff0c;学习更多免费的运维实…

深度学习之残差网络ResNet

文章目录 1. 残差网络定义2. 数学基础函数类3. 残差块4.ResNet模型5.训练模型6.小结 1. 残差网络定义 随着我们设计的网络越来越深&#xff0c;深刻理解“新添加的层如何提升神经网络的性能”变得至关重要。更重要的是设计网络的能力。在这种网络中&#xff0c;添加层会使得网…

单例模式:为何继承无法保证子类的单例特性

这里写目录标题 一、引言二、背景描述三、单例模式的规范边界全局访问点与静态工厂方法代码示例与注意事项 四、单例实现继承遇到的问题五、结论与替代方案结论替代方案特殊的想法&#x1f338;&#x1f338;源码阶段验证编译阶段验证运行阶段验证总结 一、引言 在软件设计中&a…

实时语音转文字(基于NAudio+Whisper+VOSP+Websocket)

今天花了大半天时间研究一个实时语音转文字的程序&#xff0c;目的还包括能够唤醒服务&#xff0c;并把命令提供给第三方。 由于这方面的材料已经很多&#xff0c;我就只把过程中遇到的和解决方案简单说下。源代码开源在AudioWhisper: 实时语音转文字(基于NAudioWhisperVOSPWe…

基于SSM的个性化商铺系统【附源码】

基于SSM的个性化商铺系统 效果如下&#xff1a; 用户登录界面 app首页界面 商品信息界面 店铺信息界面 用户功能界面 我的订单界面 后台登录界面 管理员功能界面 用户管理界面 商家管理界面 店铺信息管理界面 商家功能界面 个人中心界面 研究背景 研究背景 科学技术日新月异…

Leetcode 每日温度

class Solution {public int[] dailyTemperatures(int[] temperatures) {int n temperatures.length;Stack<Integer> stack new Stack<>();//默认将数组中的所有元素初始化为 0int[] results new int[n];for(int i 0; i < n; i) {while(!stack.isEmpty() &a…

leaflet前端JS实现高德地图POI兴趣点批量分类下载(附源码下载)

前言 leaflet 入门开发系列环境知识点了解&#xff1a; leaflet api文档介绍&#xff0c;详细介绍 leaflet 每个类的函数以及属性等等leaflet 在线例子leaflet 插件&#xff0c;leaflet 的插件库&#xff0c;非常有用 内容概览 leaflet前端JS实现高德地图POI兴趣点批量分类下载…

小猿口算炸鱼脚本

目录 写在前面&#xff1a; 一、关于小猿口算&#xff1a; 二、代码逻辑 1.数字识别 2.答题部分 三、代码分享&#xff1a; 补充&#xff1a;软件包下载 写在前面&#xff1a; 最近小猿口算已经被不少大学生攻占&#xff0c;小学生直呼有挂。原本是以为大学生都打着本…

【Python爬虫】看电影还在用VIP?一个python代码让你实现电影自由!附源码

今日主题 如何用Python解析vip电影。 什么是vip电影&#xff1f; 这些vip电影啊&#xff0c;想要观看的话&#xff0c;必须充值会员&#xff0c;否则没法看。 比如这个&#xff1a; 这些vip电影解析后呢&#xff1f; 不需要会员&#xff0c;不需要登录&#xff0c;可以直接…

Java-类与对象

一、面向对象 在了解类与对象前&#xff0c;我们需要先知道"面向对象"这个词的概念&#xff1a; 在Java语言中&#xff0c;我们的主要思想就是"面向对象"&#xff0c;而在之前我们所学习的C语言中大部分时候的思想是"面向过程"。 那么什么是&…

MySQL-10.DML-添加数据insert

一.DML(INSERT) -- DDL&#xff1a;数据操作语言 -- DML&#xff1a;插入数据 - insert -- 1.为tb_emp表的username&#xff0c;name&#xff0c;gender字段插入值 insert into tb_emp (username,name,gender) values (wuji,无忌,1); -- 这样会报错&#xff0c;因为create_ti…

DS堆的实际应用(10)

文章目录 前言一、堆排序建堆排序 二、TopK问题原理实战创建一个有一万个数的文件读取文件并将前k个数据创建小堆用剩余的N-K个元素依次与堆顶元素来比较将前k个数据打印出来并关闭文件 测试 三、堆的相关习题总结 前言 学完了堆这个数据结构的概念和特性后&#xff0c;我们来看…

限时设计ui

ctrl-------放大缩小 空格-----画面移动 alt------复制 页面<画板<图层 添加交互事件 原型 点击蓝色的圆&#xff0c;从1跳转到2 点击绿色的圆&#xff0c;从2跳转到1

基于SSM+Vue+MySQL的健身房管理系统

系统展示 系统背景 随着人们生活水平的提高和健康意识的增强&#xff0c;越来越多的人选择去健身房锻炼。传统的健身房管理方式往往依赖于纸质记录和人工操作&#xff0c;这种方式不仅效率低下&#xff0c;而且容易出错。为了提高健身房的管理效率和服务质量&#xff0c;开发一…