zoukankan      html  css  js  c++  java
  • 9.ThinkPHP数据库操作

    连接数据库

    在应用配置目录或者模块配置目录下面的config/database.php中配置下面的数据库参数

    image-20200525162437983

    image-20200525162443245

    注:配置好的,一定要检查mysql服务是否开启,同时也要检查pdo是否打开。

    同时还是创建好对应的数据库和连接数据库的用户名和密码并确保他们可以连接上你们的mysql服务器。

    读取配置文件中的配置

    例:

    <?php
    
    namespace appindexcontroller;
    
    use thinkController;
    
    class Db extends Controller
    {
        public function db(){
        	//database文件中的prefix选项
            echo config('database.prefix');
        }
    }
    

    访问结果

    image-20200525163516481

    执行原生的sql

    db类查询方法

    Db类支持原生SQL查询操作,主要包括下面两个方法:

    方法名 作用
    query方法 query方法用于执行SQL查询操作,如果数据非法或者查询错误则返回false,否则返回查询结果数据集(同select方法)
    execute方法 execute用于更新和写入数据的sql操作,如果数据非法或者查询错误则返回false,否则返回影响的记录数。

    参数绑定

    支持在原生查询的时候使用参数绑定,包括问号占位符或者命名占位符,例如:

    Db::query("select * from think_user where id=? AND status=?", [8, 1]);
    // 命名绑定
    Db::execute("update think_user set name=:name where status=:status", ['name' => 'thinkphp', 'status' => 1]);
    

    用法示例

    方式一

    <?php
    
    namespace appindexcontroller;
    
    use thinkController;
    use 	hinkDb as mdb;
    
    class Db extends Controller
    {
        public function db(){
            //?为占位符
            $sql = "select * from tp_articles where id=?";
            $res = mdb::query($sql,[102]);
            dump($res);
        }
    }
    

    方式二

    <?php
    
    namespace appindexcontroller;
    
    use thinkController;
    //注意引入会报错所以重命名一下
    use 	hinkDb as mdb;
    
    class Db extends Controller
    {
        public function db(){
            //:id为占位符
            //如果一定要写原生sql,推荐写此关联数组占位
            $sql = "select * from tp_articles where id=:id";
            $res = mdb::query($sql,['id' => 102]);
            dump($res);
        }
    }
    

    以上两种方式运行结果为:

    image-20200525164352008

    添加数据

    单条数据插入

    要添加的数据

    $data = ['title' => '我是标题111', 'desn' => '我是描述', 'body' => 'bbbb'];
    

    注意:方式一和方式二都要引入 hinkDb

    例:

    use 	hinkDb;
    

    方式一:Db::table 需要写全表名称

    例:

    // 添加一条数据
    // 返回影响的行数
    // table写全表名称
    $ret = Db::table('tp_articles')->insert($data);
    

    方式二:Db::name 可以不写前缀

    // name可以不写表前缀
    $ret = Db::name('articles')->insert($data);
    

    方式三:db()可以不写前缀,也不用引入db类

    $ret = db('articles') -> insert($data) ;
    

    注意上面三种运行后返回的都是影响的行数

    运行结果

    image-20200525171755076

    返回插入成功的主键ID

    $ret = db('articles') -> insertGetId($data) ;
    

    运行结果

    image-20200525171938790

    多条数据插入

    要添加的数据

    # 添加多条数据
    $data = [
                ['title' => '1111', 'body' => 'aaa'],
                ['title' => '2222', 'body' => 'bbb'],
                ['title' => '3333', 'body' => 'ccc']
            ];
    

    方式一:Db::name('表名')->insertAll($data)

    //先引入
    use 	hinkDb;
    
    $res = Db::name('articles')->insertAll($data);
    

    image-20200525174023178

    方式二:db('表名')->insertAll($data)

    $res = db('articles')->insertAll($data);
    

    image-20200525174202820

    更新数据

    全字段更新

    方式一:db()->where()->update()方式

    写法示例:

    #写法1 推荐 注意如果where条件中间是=号,则可以省略不写
    db('user')->where('id', '=', 205)->update(['name' => 'thinkphp']);
    
    #写法2
    db('user')->where('id', '=', 205)->data(['name' => 'thinkphp'])->update();
    
    #写法3 这种写法需要主键是id
    Db::name('user')->update(['name' => 'thinkphp','id'=>1]);
    
    

    例:

    public function update(){
            // 修改数据
            $data = ['title' => '我是标题111', 'desn' => '我是描述', 'body' => 'bbbb'];
            //$res = db('articles')->where('id', '=', '205')->update($data);
    
            $data = ['id' => '205','title' => '我是标题111', 'desn' => '我是描述', 'body' => 'bbbb'];
            $res = db('articles')->update($data);
            dump($res);
        }
    

    运行结果

    image-20200525181937131

    方式二:Db::raw 数值类型字段更新

    V5.1.7+版本以后,支持使用raw方法进行数据更新,适合在数组更新的情况。

    注意Db::raw支持表达式,字符串是用Db::raw 相当于值没有加引号的情况,最好是数值类型的

    写法示例:

    Db::name('user')
        ->where('id', 1)
        ->update([
            'name'		=>	Db::raw('UPPER(name)'),
            'score'		=>	Db::raw('score-3'),
            'read_time'	=>	Db::raw('read_time+1')
        ]);
    

    例:

    $res = Db::name('articles')
                ->where('id',206)
                ->update([
                    'click' => Db::raw('click+1')
                ]);
    

    运行结果

    image-20200525185928749

    单字段更新

    setField() 更新单个字段

    Db::name('user')
        ->where('id',1)
        ->setField('name', 'thinkphp');
    

    最终生成的SQL语句可能如下:

    UPDATE `think_user`  SET `name` = 'thinkphp'  WHERE  `id` = 1
    

    setField 方法返回影响数据的条数,没修改任何数据字段返回 0

    setInc/setDec 自增或自减一个字段的值

    可以使用setInc/setDec方法自增或自减一个字段的值( 如不加第二个参数,默认步长为1)。

    // score 字段加 1
    Db::table('think_user')
        ->where('id', 1)
        ->setInc('score');
    // score 字段加 5
    Db::table('think_user')
        ->where('id', 1)
        ->setInc('score', 5);
    // score 字段减 1
    Db::table('think_user')
        ->where('id', 1)
        ->setDec('score');
    // score 字段减 5
    Db::table('think_user')
        ->where('id', 1)
        ->setDec('score', 5);
    

    最终生成的SQL语句可能是:

    UPDATE `think_user`  SET `score` = `score` + 1  WHERE  `id` = 1 
    UPDATE `think_user`  SET `score` = `score` + 5  WHERE  `id` = 1
    UPDATE `think_user`  SET `score` = `score` - 1  WHERE  `id` = 1
    UPDATE `think_user`  SET `score` = `score` - 5  WHERE  `id` = 1 
    

    setInc/setDec支持延时更新,如果需要延时更新则传入第三个参数,下例中延时10秒更新。

    Db::name('user')->where('id', 1)->setInc('score', 1, 10);
    

    setInc/setDec 方法返回影响数据的条数,如果使用了延迟更新的话,可能会返回true

    删除数据

    删除写法示例

    # 根据主键删除
    Db::table('think_user')->delete(1);
    Db::table('think_user')->delete([1,2,3]);
    
    # 条件删除    
    Db::table('think_user')->where('id',1)->delete();
    Db::table('think_user')->where('id','<',10)->delete();
    
    # 无条件删除所有数据  小心去用
    Db::name('user')->delete(true);
    
    # 软删除数据 使用delete_time字段标记删除   逻辑删除
    # 软删除,必须要表中要delete_time字段,且该字段因为存放的是时间戳所以应该是int
    Db::name('user')
    	->where('id', 1)
    	->useSoftDelete('delete_time',time())
        ->delete();
    

    直接删除示例

    image-20200525193905789

    软删除示例

    public function del(){
           
            # 软删除数据 使用delete_time字段标记删除   逻辑删除
            # 软删除,必须要表中要delete_time字段 且该字段因为存放的是时间戳所以应该是int
            $res = Db::name('articles')
                ->where('id', 207)
                ->useSoftDelete('delete_time',time())
                ->delete();
            dump($res);
        }
    

    image-20200525194715742

    查询数据

    相关方法API和作用

    方法 作用 示例
    find() 查询单个数据 // table方法必须指定完整的数据表名
    Db::table('think_user')->where('id',1)->find();
    findOrFail() 如果希望在没有找到数据后抛出异常可以使用 如果没有查找到数据,则会抛出一个thinkdbexceptionDataNotFoundException异常
    Db::table('think_user')->where('id',1)->findOrFail();
    findOrEmpty() V5.1.23+版本开始,支持,当查询不存在的时候返回空数组而不是Null Db::table('think_user')->where('id',1)->findOrEmpty()
    select() 查询多个数据(数据集)使用 Db::table('think_user')->where('status',1)->select()
    selectOrFail() 如果希望在没有查找到数据后抛出异常可以使用 如果没有查找到数据,同样也会抛出一个thinkdbexceptionDataNotFoundException异常
    Db::table('think_user')->where('status',1)->selectOrFail()
    value() 查询某个字段的值可以用,value 方法查询结果不存在,返回 null // 返回某个字段的值
    Db::table('think_user')->where('id',1)->value('name');
    column() 查询某一列的值可以用,column 方法查询结果不存在,返回空数组 // 返回数组
    Db::table('think_user')->where('status',1)->column('name');
    // 指定id字段的值作为索引,也就是让id作为键name为值
    Db::table('think_user')->where('status',1)->column('name','id');
    // 指定id字段的值作为索引 返回所有数据 Db::table('think_user')->where('status',1)->column('*','id');
    order() 排序
    limit() 取某个范围的值

    单条件查询

    注意:上面的方法都能用,这里只是做个例子

    例:

    public function select(){
        //$res = db('articles')->where('id','=', 102)->find();
        $res = db('articles')->where('id','>', 200)->select();
        dump($res);
    }
    

    image-20200525223834057

    多条件查询

    例:

    public function select(){
            //id 大于100,click大于100
            //方式一
            //$res = db('articles')->where('id','>', 100)->where('click', '>', 100)->select();
    
            //方式二
            /*$where = [
                ['id', '>', 100],
                ['click', '>', 100]
            ];
            $res = db('articles')->where($where)->select();*/
    
            //方式三
            /*$where = [
                'id' => ['>', 100],
                'click' => ['>', 100]
            ];
            $obj = new Where($where);
            $res = db('articles')->where($obj)->select();*/
    
            //方式四 闭包查询
            //注意:这种方式sql会解析成这样,进行了条件分组
            //如:SELECT * FROM `tp_articles` WHERE ( `id` > 100 AND `click` > 100 ) OR ( `id` > 100 AND `click` > 100 )
            //上面的三种方式则不会,会直接解析成,没有进行条件分组
            //如: SELECT * FROM `tp_articles` WHERE `id` > 100 AND `click` > 100
            $res = db('articles')->where(function (Query $query){
                $query->where('id','>', 100)->where('click', '>', 100);
            })->whereOr(function (Query $query){
                $query->where('id','>', 100)->where('click', '>', 100);
            })->select();
            dump($res);
        }
    

    image-20200525225914914

    where条件 and,or,in

    where方法的用法是ThinkPHP查询语言的精髓,也是ThinkPHP ORM的重要组成部分和亮点所在,可以完成包括普通查询、表达式查询、快捷查询、区间查询、组合查询在内的查询操作。where方法的参数支持的变量类型包括字符串、数组和闭包。

    where方法相同用法的方法还包括whereOrwhereIn等一系列快捷查询方法,下面仅以where为例说明用法。

    AND

    主要用于等值AND条件,例如:

    // 传入数组作为查询条件
    Db::table('think_user')->where([
    	'name'	=>	'thinkphp',
        'status'=>	1
    ])->select(); 
    

    最后生成的SQL语句是

    SELECT * FROM think_user WHERE `name`='thinkphp' AND status = 1
    

    IN

    V5.1.13+版本开始增加了关联数组的IN查询支持,例如可以使用:

    // 传入数组作为查询条件
    Db::table('think_user')->where([
    	'name'	=>	'thinkphp',
        'status'=>	[1, 2]
    ])->select(); 
    

    最后生成的SQL语句是

    SELECT * FROM think_user WHERE `name`='thinkphp' AND status IN (1, 2)
    

    OR

    $res = db('articles')->where(function (Query $query){
    	$query->where('id','>', 100)->where('click', '>', 100);
    })->whereOr(function (Query $query){
    	$query->where('id','>', 100)->where('click', '>', 100);
    })->select();
    

    最后生成的SQL语句是

    SELECT * FROM `tp_articles` WHERE ( `id` > 100 AND `click` > 100 ) OR ( `id` > 100 AND `click` > 100 )
    

    字符串条件

    使用字符串条件直接查询和操作,例如:

    Db::table('think_user')->where('type=1 AND status=1')->select(); 
    

    最后生成的SQL语句是

    SELECT * FROM think_user WHERE type=1 AND status=1
    

    注意使用字符串查询条件和表达式查询的一个区别在于,不会对查询字段进行避免关键词冲突处理。

    使用字符串条件的时候,如果需要传入变量,建议配合预处理机制,确保更加安全,例如:

    Db::table('think_user')
    ->where("id=:id and username=:name", ['id' => [1, PDO::PARAM_INT] , 'name' => 'thinkphp'])
    ->select();
    

    或者使用

    Db::table('think_user')
    ->where("id=:id and username=:name")
    ->bind(['id' => [1, PDO::PARAM_INT] , 'name' => 'thinkphp'])
    ->select();
    

    V5.1.7+版本以后,你可以使用更安全的

    Db::table('think_user')
    ->whereRaw("id=:id and username=:name", ['id' => [1, PDO::PARAM_INT] , 'name' => 'thinkphp'])
    ->select();
    

    排序和分页

    $res = db('articles')->order('id', 'desc')->limit(0,2)->select();
    

    例:

    image-20200525231532819

    聚合查询

    在应用中我们经常会用到一些统计数据,例如当前所有(或者满足某些条件)的用户数、所有用户的最大积分、用户的平均成绩等等,ThinkPHP为这些统计操作提供了一系列的内置方法,包括:

    方法 说明
    count 统计数量,参数是要统计的字段名(可选)
    max 获取最大值,参数是要统计的字段名(必须)
    min 获取最小值,参数是要统计的字段名(必须)
    avg 获取平均值,参数是要统计的字段名(必须)
    sum 获取总分,参数是要统计的字段名(必须)

    聚合方法如果没有数据,默认都是0,聚合查询都可以配合其它查询条件

    V5.1.5+版本开始,聚合查询可以支持JSON字段类型

    用法示例

    获取用户数:

    Db::table('think_user')->count();
    

    实际生成的SQL语句是:

    SELECT COUNT(*) AS tp_count FROM `think_user` LIMIT 1
    

    或者根据字段统计:

    Db::table('think_user')->count('id');
    

    生成的SQL语句是:

    SELECT COUNT(id) AS tp_count FROM `think_user` LIMIT 1
    

    获取用户的最大积分:

    Db::table('think_user')->max('score');
    

    生成的SQL语句是:

    SELECT MAX(score) AS tp_max FROM `think_user` LIMIT 1
    

    如果你要获取的最大值不是一个数值,可以使用第二个参数关闭强制转换

    Db::table('think_user')->max('name',false);
    

    获取积分大于0的用户的最小积分:

    Db::table('think_user')->where('score', '>', 0)->min('score');
    

    和max方法一样,min也支持第二个参数用法

    Db::table('think_user')->where('score', '>', 0)->min('name',false);
    

    获取用户的平均积分:

    Db::table('think_user')->avg('score');
    

    生成的SQL语句是:

    SELECT AVG(score) AS tp_avg FROM `think_user` LIMIT 1
    

    统计用户的总成绩:

    Db::table('think_user')->where('id',10)->sum('score');
    

    生成的SQL语句是:

    SELECT SUM(score) AS tp_sum FROM `think_user` LIMIT 1
    

    获取器(V5.1.20+

    Db类也可以支持获取器定义,例如:

    Db::name('user')->withAttr('name', function($value, $data) {
    	return strtolower($value);
    })->select();
    

    上面的代码,查询的数据集数据中的name字段的值会统一进行小写转换。

    withAttr方法可以多次调用,对多个字段定义获取器。

    支持对JSON字段定义获取器,例如:

    $user = Db::name('user')
    	->json(['info'])
        ->withAttr('info.name', function($value, $data) {
            return strtolower($value);
        })->find(1);
    dump($user);    
    

    查询结果返回的时候,会自动对info字段(JSON字段)的name属性使用获取器操作。

    例:

    //获取器                                            当前数据,数据源
    $res = db('articles')->withAttr('title',function ($value,$data){
        //重新编辑的数据
        return '获取器-----'.$value;
    })->where('id','>', 200)->select();
    

    运行结果

    image-20200525233500620

  • 相关阅读:
    oracle中add_months()函数总结
    Oracle总结之plsql编程(基础九)
    Oracle总结之plsql编程(基础八)
    java调用存储过程
    Oracle总结之plsql编程(基础七)
    Python 變量 Variable 動態綁定
    Python 類和對象 Class vs Object
    Python 元組 Tuple
    Python 字典 Dictionary
    Python 列表 List
  • 原文地址:https://www.cnblogs.com/makalochen/p/12961778.html
Copyright © 2011-2022 走看看