当前位置: 首页 > news >正文

ThinkPHP 8模型与数据的插入、更新、删除

【图书介绍】《ThinkPHP 8高效构建Web应用》-CSDN博客

《2025新书 ThinkPHP 8高效构建Web应用 编程与应用开发丛书 夏磊 清华大学出版社教材书籍 9787302678236 ThinkPHP 8高效构建Web应用》【摘要 书评 试读】- 京东图书

使用VS Code开发ThinkPHP项目-CSDN博客

编程与应用开发_夏天又到了的博客-CSDN博客

8.1  模型定义

定义模型非常简单,继承think\Model即可。下面是一个用户模型的示例:

<?php
namespace app\model;use think\Model;class User extends Model
{}

默认情况下,模型类名是去除表前缀的数据表名称,采用大驼峰命名法。比如下面的示例:

  • User <-> think_user
  • UserWallet <-> think_user_wallet

模型的$table属性可以手动指定数据表名称,下面是一个数据表为users的模型示例:

【示例8-1】

<?php
namespace app\model;use think\Model;class User extends Model
{protected $table='users'; // 手动指定数据表名称}

其他常用的模型属性包括$pk和$connection。$pk用来指定主键字段,默认为id,如果数据表主键不是id,则需要重新定义。$connection用来指定模型使用的数据库连接。

下面是一个指定主键和数据库连接的示例。

【示例8-2】

<?php
namespace app\model;use think\Model;class User extends Model
{protected $pk = 'user_id';         // 指定主键,多对多关联中必须指定主键protected $connection = 'user';    // 手动指定数据表名称
}

模型字段用来指定模型属性的数据类型,推荐每个模型类都进行定义,ThinkPHP 8默认会自动获取数据表的字段类型(需要查询一次数据库)。在生产实践中一般会开启字段缓存,以避免频繁获取字段类型的开销。

模型的数据字段和对应数据表的字段是对应的,默认会自动获取(包括字段类型),但自动获取会导致增加一次查询(可以开启字段缓存功能),因此需要在模型中明确定义字段信息以避免多一次查询的开销。下面是一个手动定义模型字段的示例。

【示例8-3】

<?php
namespace app\model;use think\Model;class User extends Model
{// 设置字段信息protected $schema = ['id'          => 'int','username'        => 'string','password'      => 'string','age' => 'int','balance'       => 'float','created_at' => 'datetime','updated_at' => 'datetime',];
}

上述代码中,模型字段对应数据库中的User表字段,$schema属性需要定义所有字段。如果只需要手动指定某些字段的数据类型,则可以使用$type属性,示例如下:

【示例8-4】

<?php
namespace app\model;use think\Model;class User extends Model
{// 设置字段信息protected $type = ['balance'       => 'float',];
}

8.2  插入数据

使用模型插入数据和查询构造器插入数据,最大的不同是模型会执行修改器、自动完成等逻辑,而数据库操作只是单纯的数据插入。

在调用模型实例的save方法插入数据时,如果插入成功,则返回true,否则会抛出异常。

【示例8-5】

本示例演示每个字段单独赋值。首先在mydb库中创建一张表,语句为:

CREATE TABLE `users` (`id` int NOT NULL AUTO_INCREMENT,`name` varchar(45) NOT NULL,`nickname` varchar(45) NOT NULL,`status` int DEFAULT '0',PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8mb3;

控制器User代码如下:

<?php
namespace app\controller;use app\model\UserModel;class User {public function create() {$user = new UserModel();$data = ['name' => 'John Doe','nickname' => 'John Bull','status' => 1];$result = $user->save($data);if ($result) {return '创建成功';} else {return '创建失败';}}
}

对应的Model为app\model\UserModel.php,代码如下:

<?php
namespace app\model;use think\Model;class UserModel extends Model {// 设置当前模型对应的完整数据表名称protected $table = 'users';// 设置模型名称protected $name = 'user';// 设置可以批量赋值的字段列表protected $field = ['id', 'name', 'nickname', 'status'];
}

启动服务器,在浏览器中访问http://localhost:8000/user/create,页面将提示“创建成功”。当然,ThinkPHP 8也提供批量赋值的方法:

$user = new User;
$user->save(['name' => 'Bruce Lee','nickname' => 'Lee three foots','status' => 1
]);

1. REPLACE语句插入

REPLACE语句在数据库中通常用于插入新行或更新现有行。其工作原理类似于INSERT语句,但当新行与一个已有的行(根据PRIMARY KEY或UNIQUE索引)产生唯一性约束冲突时,旧行将被删除,然后新行被插入。因此,它可以视为一个删除(如果有需要)和插入的组合操作。

调用模型的replace方法可以进行REPLACE插入:

$user = new User;$user->replace()->save(['username' => 'test','password' => password_hash('test', PASSWORD_DEFAULT);]);

2. 批量插入

调用模型实例的saveAll方法可以批量插入数据。当数据行包含主键时,ThinkPHP 8会执行更新操作,否则执行插入操作,代码如下:

$user = new User;$list = [['name'=> 'test','age' => 20], // 识别为插入操作['id' => 2,'name'=> 'test1','age' => 21], // 识别为更新操作];$user->saveAll($list);

3. create方法插入

使用模型类的create方法插入数据是一种常用的方法,它可以返回模型实例,代码如下:

$user = User::create(['name'  =>  'test','age' =>  20]);

8.3  更新数据

save方法会自动根据是否有主键来决定执行插入和更新操作,无须开发者手动调用更新方法。对于更新操作,一般需要先查询出模型实例,给对应的字段赋值,最后调用save方法更新数据,下面是一个示例:

$user = User::where('username','test')->find();
if(!empty($user)) {$user->age = 20;$user->save();
}

还可以使用模型类的update方法更新数据,返回对应的模型实例:

User::update(['age' => 20], ['id' => 1]);

8.4  删除数据

使用模型来删除数据,会执行模型的事件处理逻辑;而直接使用查询构造器删除数据,则不会执行模型的事件处理逻辑。下面是几种删除数据的方法:

$user = User::find(1);
$user->delete(); // 调用模型实例的delete方法User::destroy(1); // 静态方法删除
User::destroy([1,2,3]); // 支持批量删除多个数据User::where('age', '<', 20)->delete(); // 基于where条件删除

相关文章:

ThinkPHP 8模型与数据的插入、更新、删除

【图书介绍】《ThinkPHP 8高效构建Web应用》-CSDN博客 《2025新书 ThinkPHP 8高效构建Web应用 编程与应用开发丛书 夏磊 清华大学出版社教材书籍 9787302678236 ThinkPHP 8高效构建Web应用》【摘要 书评 试读】- 京东图书 使用VS Code开发ThinkPHP项目-CSDN博客 编程与应用开…...

c语言函数(详解)

目录 前言 一、函数的基本概念和作用 二、函数的声明和定义 三、函数参数的传递方式 四、函数的递归 五、函数指针 总结 前言 本文主要讲解了c语言函数方面的内容 函数的定义和调用函数的返回值和参数函数的作用域和生命周期 函数的声明和定义 函数声明和函数定义的区别函数声…...

为AI聊天工具添加一个知识系统 之70 详细设计 之11 维度运动控制的应用:上下文受控的自然语言

本文要点 要点 前面我们 讨论了 “维度”及其运动控制原理 以及 维度控制 如何在中台微服务架构中撑起了“架构师”角色的一片天。下面我们从 “维度”运动控制的一个典型应用场景&#xff1a;受控的自然语言 ”开始讨论。 拼块文字型风格: 维度运动控制下的受控自然语言…...

ios打包:uuid与udid

ios的uuid与udid混乱的网上信息 新人开发ios&#xff0c;发现uuid和udid在网上有很多帖子里是混淆的&#xff0c;比如百度下&#xff0c;就会说&#xff1a; 在iOS中使用UUID&#xff08;通用唯一识别码&#xff09;作为永久签名&#xff0c;通常是指生成一个唯一标识&#xf…...

数组,对象解构,forEach方法,filter方法

数组解构 对象结构 遍历数组 forEach方法 筛选数组 filter方法 渲染商品案例 forEach遍历数组&#xff0c;能得到每个数组中的数据&#xff0c;item是对象中的每个元素 将遍历的数组中每个对象 加到 str 中 将 str 字符串中的 8 个 div 添加到 list盒子中 对象解构并渲染 综…...

PSPNet

文章目录 摘要Abstract1. 引言2. 框架2.1 金字塔池化模块2.2 特征提取器的监督2.3 训练细节 3. 创新点和不足3.1 创新点3.2 不足 参考总结 摘要 PSPNet是一个改进了FCN-8s缺点的语义分割模型&#xff0c;它解决了FCN-8s的缺点——分割不够精细以及没有考虑上下文信息。PSPNet的…...

论文阅读的附录(七):Understanding Diffusion Models: A Unified Perspective(二):公式46的推导

Understanding Diffusion Models: A Unified Perspective&#xff08;二&#xff09;&#xff1a;公式46的推导 文章概括要推导的公式1. 条件概率的定义2. 联合分布的分解2.1 联合分布的定义2.2 为什么可以这样分解&#xff1f;2.3 具体意义 3. 分母的分解&#xff1a;边际化规…...

BGP分解实验·12——配置路由反射器

当一个AS包含多个iBGP对等体时&#xff0c;路由反射器&#xff08;Route-Reflector&#xff09;非常有用&#xff0c;因为相对于iBGP路由反射器指定的客户端只需要和路由反射器建立邻居关系&#xff0c;从而降低了iBGP全互连的连接数量。路由反射器&#xff08;RR&#xff09;和…...

PCIe 个人理解专栏——【2】LTSSM(Link Training and Status State Machine)

前言&#xff1a; 链路训练和状况状态机LTSSM&#xff08;Link Training and Status State Machine&#xff09;是整个链路训练和运行中状态的状态转换逻辑关系图&#xff0c;总共有11个状态。 正文&#xff1a; 包括检测&#xff08;Detect&#xff09;&#xff0c;轮询&…...

cmake 编译QT之JKQtPlotter-4.0.3

cmake 编译 JKQtPlotter-4.0.3 1.下载源码 源码地址&#xff1a;https://github.com/jkriege2/JKQtPlotter 2.编译 mkdir build cd buildDCMAKE_PREFIX_PATH指编译器目录 D:\ProgramFiles\cmake-3.25.0-rc1-windows-i386\bin\cmake.exe -G "Visual Studio 16 2019&qu…...

【C】memory 详解

<memory.h> 是一个 C 标准库头文件&#xff0c;提供了一组内存管理函数&#xff0c;用于分配、释放和操作动态内存。这些函数主要操作的是未初始化的内存块&#xff0c;是早期 C 编程中常用的内存操作工具。 尽管在现代 C 编程中更推荐使用<cstring>或<memory&…...

Python 爬虫 - Selenium 框架

Python 爬虫 - Selenium 框架 安装安装 Selenium安装 WebDriver 操作浏览器打开浏览器普通方式加载配置方式Headless 方式 设置浏览器窗口最大化显示最小化显示自定义大小 前进后退前进后退 元素定位根据 id 定位根据 name 定位根据 class 定位根据标签名定位使用 CSS 定位使用…...

mysql的having语句

MySQL的HAVING语句用于在GROUP BY子句对数据进行分组后&#xff0c;过滤满足特定条件的组。与WHERE子句不同&#xff0c;HAVING子句可以在过滤条件中使用聚合函数&#xff0c;而WHERE子句则不能。通常&#xff0c;HAVING子句与GROUP BY子句一起使用&#xff0c;以实现对分组数据…...

华为数据之道-读书笔记

内容简介 关键字 数字化生产 已经成为普遍的商业模式&#xff0c;其本质是以数据为处理对象&#xff0c;以ICT平台为生产工具&#xff0c;以软件为载体&#xff0c;以服务为目的的生产过程。 信息与通信技术平台&#xff08;Information and Communication Technology Platf…...

CDN、源站与边缘网络

什么是“源站” 源服务器 源服务器的目的是处理和响应来自互联网客户端的传入请求。源服务器的概念通常与边缘服务器或缓存服务器的概念结合使用。源服务器的核心是一台运行一个或多个程序的计算机&#xff0c;这些程序旨在侦听和处理传入的客户端请求。源服务器可以承担为网…...

工业相机 SDK 二次开发-Sherlock插件

本文介绍了 sherlock 连接相机时的插件使用。通过本套插件可连接海康的工业相机。 一&#xff0e;环境配置 1. 拷贝动态库 在用户安装 MVS 目录下按照如下路径 Development\ThirdPartyPlatformAdapter 找到目 录为 DalsaSherlock 的文件夹&#xff0c;根据 Sherlock 版本找到…...

FlinkSql使用中rank/dense_rank函数报错空指针

问题描述 在flink1.16(甚至以前的版本)中&#xff0c;使用rank()或者dense_rank()进行排序时&#xff0c;某些场景会导致报错空指针NPE(NullPointerError) 报错内容如下 该报错没有行号/错误位置&#xff0c;无法排查 现状 目前已经确认为bug&#xff0c;根据github上的PR日…...

VS C++ 配置OPENCV环境

VS C 配置OPENCV环境 1.下载opencv2.安装环境3.opencv环境4.VS配置opencv环境5.EXE执行文件路径的环境lib和dll需要根据是debug还是release环境来区分使用哪个 6.Windows环境 1.下载opencv 链接: link 2.安装环境 双击运行即可 3.opencv环境 include文件路径:opencv\build\…...

【SpringSecurity】基本开发流程

文章目录 概要整体架构流程实现流程1、编写各种Handler2 、AccessToken处理器3、定义AuthenticationFilter 继承 OncePerRequestFilter &#xff08;OncePerRequestFilter是Spring提供的一个过滤器基类&#xff0c;它确保了在一次完整的HTTP请求中&#xff0c;无论请求经过多少…...

Redis实战(黑马点评)——关于缓存(缓存更新策略、缓存穿透、缓存雪崩、缓存击穿、Redis工具)

redis实现查询缓存的业务逻辑 service层实现 Overridepublic Result queryById(Long id) {String key CACHE_SHOP_KEY id;// 现查询redis内有没有数据String shopJson (String) redisTemplate.opsForValue().get(key);if(StrUtil.isNotBlank(shopJson)){ // 如果redis的数…...

Chapter03-Authentication vulnerabilities

文章目录 1. 身份验证简介1.1 What is authentication1.2 difference between authentication and authorization1.3 身份验证机制失效的原因1.4 身份验证机制失效的影响 2. 基于登录功能的漏洞2.1 密码爆破2.2 用户名枚举2.3 有缺陷的暴力破解防护2.3.1 如果用户登录尝试失败次…...

java调用dll出现unsatisfiedLinkError以及JNA和JNI的区别

UnsatisfiedLinkError 在对接硬件设备中&#xff0c;我们会遇到使用 java 调用 dll文件 的情况&#xff0c;此时大概率出现UnsatisfiedLinkError链接错误&#xff0c;原因可能有如下几种 类名错误包名错误方法名参数错误使用 JNI 协议调用&#xff0c;结果 dll 未实现 JNI 协…...

定时器任务——若依源码分析

分析util包下面的工具类schedule utils&#xff1a; ScheduleUtils 是若依中用于与 Quartz 框架交互的工具类&#xff0c;封装了定时任务的 创建、更新、暂停、删除等核心逻辑。 createScheduleJob createScheduleJob 用于将任务注册到 Quartz&#xff0c;先构建任务的 JobD…...

ElasticSearch搜索引擎之倒排索引及其底层算法

文章目录 一、搜索引擎1、什么是搜索引擎?2、搜索引擎的分类3、常用的搜索引擎4、搜索引擎的特点二、倒排索引1、简介2、为什么倒排索引不用B+树1.创建时间长,文件大。2.其次,树深,IO次数可怕。3.索引可能会失效。4.精准度差。三. 倒排索引四、算法1、Term Index的算法2、 …...

鱼香ros docker配置镜像报错:https://registry-1.docker.io/v2/

使用鱼香ros一件安装docker时的https://registry-1.docker.io/v2/问题 一键安装指令 wget http://fishros.com/install -O fishros && . fishros出现问题&#xff1a;docker pull 失败 网络不同&#xff0c;需要使用镜像源 按照如下步骤操作 sudo vi /etc/docker/dae…...

零基础设计模式——行为型模式 - 责任链模式

第四部分&#xff1a;行为型模式 - 责任链模式 (Chain of Responsibility Pattern) 欢迎来到行为型模式的学习&#xff01;行为型模式关注对象之间的职责分配、算法封装和对象间的交互。我们将学习的第一个行为型模式是责任链模式。 核心思想&#xff1a;使多个对象都有机会处…...

Unit 1 深度强化学习简介

Deep RL Course ——Unit 1 Introduction 从理论和实践层面深入学习深度强化学习。学会使用知名的深度强化学习库&#xff0c;例如 Stable Baselines3、RL Baselines3 Zoo、Sample Factory 和 CleanRL。在独特的环境中训练智能体&#xff0c;比如 SnowballFight、Huggy the Do…...

【数据分析】R版IntelliGenes用于生物标志物发现的可解释机器学习

禁止商业或二改转载&#xff0c;仅供自学使用&#xff0c;侵权必究&#xff0c;如需截取部分内容请后台联系作者! 文章目录 介绍流程步骤1. 输入数据2. 特征选择3. 模型训练4. I-Genes 评分计算5. 输出结果 IntelliGenesR 安装包1. 特征选择2. 模型训练和评估3. I-Genes 评分计…...

Android第十三次面试总结(四大 组件基础)

Activity生命周期和四大启动模式详解 一、Activity 生命周期 Activity 的生命周期由一系列回调方法组成&#xff0c;用于管理其创建、可见性、焦点和销毁过程。以下是核心方法及其调用时机&#xff1a; ​onCreate()​​ ​调用时机​&#xff1a;Activity 首次创建时调用。​…...

JVM虚拟机:内存结构、垃圾回收、性能优化

1、JVM虚拟机的简介 Java 虚拟机(Java Virtual Machine 简称:JVM)是运行所有 Java 程序的抽象计算机,是 Java 语言的运行环境,实现了 Java 程序的跨平台特性。JVM 屏蔽了与具体操作系统平台相关的信息,使得 Java 程序只需生成在 JVM 上运行的目标代码(字节码),就可以…...