美高梅平台下载-美高梅娱乐平台登录

热门关键词: 美高梅平台下载,美高梅娱乐平台登录

模型定义, // 这要会更好

日期:2020-02-06编辑作者:美高梅平台下载

模型定义,默认情况下,ThinkPHP的模型类是位于/Home/Model/目录之下,模型类通常需要继承系统的ThinkModel类或其子类,下面是一个HomeModelUserModel类的定义:

TP细节总结1

关联模型的底层在ThinkPHP包ExtendModelRelationModel.class.php

文件命名遵守UserModel.class.php的方式,跟控制器的命名一样

  1. 接收参数尽量使用I函数,代替post、get 更安全!

    I('变量类型.变量名/修饰符',['默认值'],['过滤方法'],['额外数据源'])

  2. 在where 条件处尽量使用 array方式where(array('id'=>$id))

关联关系

通常我们所说的关联关系包括下面三种:
一对一关联 :ONE_TO_ONE,包括HAS_ONE和BELONGS_TO
一对多关联 :ONE_TO_MANY,包括HAS_MANY和BELONGS_TO
多对多关联 :MANY_TO_MANY
关联关系必然有一个参照表,例如:
有一个员工档案管理系统项目,这个项目要包括下面的一些数据表:基本信息表、员工档案表、部门表、项目组表、银行卡表(用来记录员工的银行卡资料)。
这些数据表之间存在一定的关联关系,我们以员工基本信息表为参照来分析和其他表之间的关联:
每个员工必然有对应的员工档案资料,所以属于HAS_ONE关联;
每个员工必须属于某个部门,所以属于BELONGS_TO关联;
每个员工可以有多个银行卡,但是每张银行卡只可能属于一个员工,因此属于HAS_MANY关联;
每个员工可以同时在多个项目组,每个项目组同时有多个员工,因此属于MANY_TO_MANY关联;
分析清楚数据表之前的关联关系后,我们才可以进行关联定义和关联操作。

模型类的作用大多数情况是操作数据表的,如果按照系统的规范来命名模型类的话,大多数情况下是可以自动对应数据表,但你可以根据自己的需求来定制自己的数据表设置和操作。首先我们需要在配置文件设置我们的数据库连接信息: 'DB_TYPE' => 'mysql', 'DB_HOST' => 'localhost', 'DB_NAME' => 'database', 'DB_USER' => 'username', 'DB_PWD' => 'password', 'DB_PORT' => '3306', 
  1. 在使用myql 进行查询时,若只有一条数据,用limit 1 做限制,加快查询

  2. 随机挑一条记录

关联定义

ThinkPHP可以很轻松的完成数据表的关联CURD操作,目前支持的关联关系包括下面四种:HAS_ONE、BELONGS_TO、HAS_MANY和MANY_TO_MANY
一个模型根据业务模型的复杂程度可以同时定义多个关联,不受限制,所有的关联定义都统一在模型类的 $_link 成员变量里面定义,并且可以支持动态定义。要支持关联操作,模型类必须继承RelationModel类,关联定义的格式是:

protected $_link = array(      '关联1'  =>  array(          '关联属性1' => '定义',          '关联属性N' => '定义',      ),      '关联2'  =>  array(          '关联属性1' => '定义',          '关联属性N' => '定义',      ),      '关联3'  =>  HAS_ONE, // 快捷定义      ...  );  

 下面我们首先来分析下各个关联方式的定义:
HAS_ONE
HAS_ONE关联表示当前模型拥有一个子对象,例如,每个员工都有一个人事档案。我们可以建立一个用户模型UserModel,并且添加如下关联定义:

class UserModel extends RelationModel{      protected $_link = array(         'Profile'=> HAS_ONE,      );  }  

 上面是最简单的方式,表示其遵循了系统内置的数据库规范,完整的定义方式是:

class UserModel extends RelationModel{      protected $_link = array(              'Profile'=>array(              'mapping_type'    =>HAS_ONE,                   'class_name'    =>'Profile',                   // 定义更多的关联属性                ……               ),           );  }  

 关联HAS_美高梅平台下载 ,ONE支持的关联属性有:

 

mapping_type 关联类型,这个在HAS_ONE 关联里面必须使用HAS_ONE 常量定义。
class_name 要关联的模型类名
例如,class_name 定义为Profile的话则表示和另外的Profile模型类关联,这个Profile模型类是无需定义的,系统会自动定位到相关的数据表进行关联。
mapping_name 关联的映射名称,用于获取数据用
该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。如果mapping_name没有定义的话,会取class_name的定义作为mapping_name。如果class_name也没有定义,则以数组的索引作为mapping_name。
foreign_key 关联的外键名称
外键的默认规则是当前数据对象名称_id,例如:
UserModel对应的可能是表think_user (注意:think只是一个表前缀,可以随意配置)
那么think_user表的外键默认为 user_id,如果不是,就必须在定义关联的时候显式定义 foreign_key 。
condition 关联条件
关联查询的时候会自动带上外键的值,如果有额外的查询条件,可以通过定义关联的condition属性。
mapping_fields 关联要查询的字段
默认情况下,关联查询的关联数据是关联表的全部字段,如果只是需要查询个别字段,可以定义关联的mapping_fields属性。
as_fields

直接把关联的字段值映射成数据对象中的某个字段
这个特性是ONE_TO_ONE 关联特有的,可以直接把关联数据映射到数据对象中,而不是作为一个关联数据。当关联数据的字段名和当前数据对象的字段名称有冲突时,还可以使用映射定义。    

BELONGS_TO
Belongs_to 关联表示当前模型从属于另外一个父对象,例如每个用户都属于一个部门。我们可以做如下关联定义。

'Dept'=> BELONGS_TO  

 完整方式定义为:

'Dept'=> array(         'mapping_type'=>BELONGS_TO,            'class_name'=>'Dept',            'foreign_key'=>'userId',            'mapping_name'=>'dept',             // 定义更多的关联属性          ……  ),  

 关联BELONGS_TO定义支持的关联属性有:

 

class_name 要关联的模型类名
mapping_name 关联的映射名称,用于获取数据用
该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。
foreign_key 关联的外键名称
mapping_fields 关联要查询的字段
condition 关联条件
parent_key 自引用关联的关联字段
默认为parent_id
自引用关联是一种比较特殊的关联,也就是关联表就是当前表。
as_fields 直接把关联的字段值映射成数据对象中的某个字段

HAS_MANY
HAS_MANY 关联表示当前模型拥有多个子对象,例如每个用户有多篇文章,我们可以这样来定义:

'Article'=> HAS_MANY  

 完整定义方式为:

'Article'=> array(        'mapping_type'=>HAS_MANY,                      'class_name'=>'Article',                      'foreign_key'=>'userId',                      'mapping_name'=>'articles',                      'mapping_order'=>'create_time desc',           // 定义更多的关联属性          ……         ),  

 关联HAS_MANY定义支持的关联属性有:

 

class_name 要关联的模型类名
mapping_name 关联的映射名称,用于获取数据用
该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。
foreign_key 关联的外键名称
外键的默认规则是当前数据对象名称_id,例如:
UserModel对应的可能是表think_user (注意:think只是一个表前缀,可以随意配置)
那么think_user表的外键默认为 user_id,如果不是,就必须在定义关联的时候定义 foreign_key 。
parent_key 自引用关联的关联字段
默认为parent_id
condition 关联条件
关联查询的时候会自动带上外键的值,如果有额外的查询条件,可以通过定义关联的condition属性。
mapping_fields 关联要查询的字段
默认情况下,关联查询的关联数据是关联表的全部字段,如果只是需要查询个别字段,可以定义关联的mapping_fields属性。
mapping_limit 关联要返回的记录数目
mapping_order 关联查询的排序

MANY_TO_MANY
MANY_TO_MANY 关联表示当前模型可以属于多个对象,而父对象则可能包含有多个子对象,通常两者之间需要一个中间表类约束和关联。例如每个用户可以属于多个组,每个组可以有多个用户:

'Group'=>MANY_TO_MANY  

 完整定义方式为:

array('mapping_type'=>MANY_TO_MANY,  'class_name'=>'Group',  'mapping_name'=>'groups',  'foreign_key'=>'userId',  'relation_foreign_key'=>'goupId',  'relation_table'=>'think_gourpUser'  )  

 MANY_TO_MANY支持的关联属性定义有:

 

class_name 要关联的模型类名
mapping_name 关联的映射名称,用于获取数据用
该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。
foreign_key 关联的外键名称
外键的默认规则是当前数据对象名称_id
relation_foreign_key 关联表的外键名称
默认的关联表的外键名称是表名_id
mapping_limit 关联要返回的记录数目
mapping_order 关联查询的排序
relation_table 多对多的中间关联表名称

多对多的中间表默认表规则是:数据表前缀_关联操作的主表名_关联表名
如果think_user 和 think_group 存在一个对应的中间表,默认的表名应该是
如果是由group来操作关联表,中间表应该是 think_group_user,如果是从user表来操作,那么应该是think_user_group,也就是说,多对多关联的设置,必须有一个Model类里面需要显式定义中间表,否则双向操作会出错。
中间表无需另外的id主键(但是这并不影响中间表的操作),通常只是由 user_id 和 group_id 构成。
默认会通过当前模型的getRelationTableName方法来自动获取,如果当前模型是User,关联模型是Group,那么关联表的名称也就是使用 user_group这样的格式,如果不是默认规则,需要指定relation_table属性。

这些配置信息还是在/Home/Conf/config.php文件里设置。

// 千万不要这样做:

关联查询

由于性能问题,新版取消了自动关联查询机制,而统一使用relation方法进行关联操作,relation方法不但可以启用关联还可以控制局部关联操作,实现了关联操作一切尽在掌握之中。

$User = D("User");  $user =    $User->relation(true)->find(1);  

 输出$user结果可能是类似于下面的数据:

array(  'id'        =>    1,  'account'    =>    'ThinkPHP',  'password'    =>    '123456',  'Profile'    => array(  'email'        =>'liu21st@gmail.com',  'nickname'    =>'流年',     ),   )  

 我们可以看到,用户的关联数据已经被映射到数据对象的属性里面了。其中Profile就是关联定义的mapping_name属性。
如果我们按照下面的方式定义了as_fields属性的话,

    protected $_link = array(          'profile'=>array(      'mapping_type'    =>HAS_ONE,                      'class_name'    =>'Profile',      'foreign_key'=>'userId',      'as_fields'=>'email,nickname',           ),  );  

查询的结果就变成了下面的结果

array(  'id'        =>    1,  'account'    =>    'ThinkPHP',  'password'    =>    'name',  'email'        =>'liu21st@gmail.com',  'nickname'    =>'流年',   )  

 email和nickname两个字段已经作为user数据对象的字段来显示了。
如果关联数据的字段名和当前数据对象的字段有冲突的话,怎么解决呢?
我们可以用下面的方式来变化下定义:
'as_fields'=>'email,nickname:username',
表示关联表的nickname字段映射成当前数据对象的username字段。
默认会把所有定义的关联数据都查询出来,有时候我们并不希望这样,就可以给relation方法传入参数来控制要关联查询的。

$User = D("User");  $user =    $User->relation('Profile')->find(1);  

 关联查询一样可以支持select方法,如果要查询多个数据,并同时获取相应的关联数据,可以改成:

$User = D("User");  $list =    $User->relation(true)->Select();  

 如果希望在完成的查询基础之上 再进行关联数据的查询,可以使用

$User = D("User");  $user = $User->find(1);  // 表示对当前查询的数据对象进行关联数据获取  $profile = $User->relationGet("Profile");  

 事实上,除了当前的参考模型User外,其他的关联模型是不需要创建的。

指定数据表前缀

$r = mysql_query("SELECT username FROM user ORDER BY RAND() LIMIT 1");

关联操作

除了关联查询外,系统也支持关联数据的自动写入、更新和删除
关联写入

$User = D("User");  $data = array();  $data["account"]    = "ThinkPHP";  $data["password"] = "123456";  $data["Profile"]    = array(      'email'    =>'liu21st@gmail.com',      'nickname'    =>'流年',  );  $result =$User->relation(true)->add($data);  

 这样就会自动写入关联的Profile数据。
同样,可以使用参数来控制要关联写入的数据:

$result = $User->relation("Profile")->add($data);  

 关联更新
数据的关联更新和关联写入类似

$User = D("User");  $data["account"]    = "ThinkPHP";  $data["password"] = "123456";  $data["Profile"]    = array(      'email'    =>'liu21st@gmail.com',      'nickname'    =>'流年',  );  $result = $User-> relation(true)->where('id=3')->save($data);  

 Relation(true)会关联保存User模型定义的所有关联数据,如果只需要关联保存部分数据,可以使用:

$result = $User->relation("Profile")->save($data);  

 这样就只会同时更新关联的Profile数据。
关联保存的规则:
HAS_ONE: 关联数据的更新直接赋值
HAS_MANY: 的关联数据如果传入主键的值 则表示更新 否则就表示新增
MANY_TO_MANY: 的数据更新是删除之前的数据后重新写入关联删除
删除用户ID为3的记录的同时删除关联数据

$result = $User->relation(true)->delete("3");  

 如果只需要关联删除部分数据,可以使用

$result = $User->relation("Profile")->delete("3");  

 


指定标前缀,我们在第一课的配置项已经指定,以下的文字表示你可以灵活配置你的数据表。

 

protected $tablePrefix = 'top_';

 // 这要会更好:

如果数据库的表没有表前缀,使用空字符串代替

$r = mysql_query("SELECT count(*) FROM user");

protected $tablePrefix = '';

$d = mysql_fetch_row($r);

指定数据表,此处的指定的数据表的不需要添加表前缀:

$rand = mt_rand(0,$d[0] - 1);

protected $tableName = 'user';

$r = mysql_query("SELECT username FROM user LIMIT $rand, 1");

举个例子说,比如说你的数据库中有一个没有表前缀的,名为users的数据表,可以用以下的两种方法在模型中进行下面的定义:

  1. 关联操作

第一,直接根据系统的规范来命名模型类来命名模型,比如说就命名为UsersModel那么只需要在这个类里面加上下面的设置就可以了:

protected $tablePrefix = '';
  1. 关联模型

  2. 关联关系

    通常我们所说的关联关系包括下面三种:

    一对一关联 :ONE_TO_ONE,包括HAS_ONE 和 BELONGS_TO

    一对多关联 :ONE_TO_MANY,包括HAS_MANY 和 BELONGS_TO

    多对多关联 :MANY_TO_MANY

    关联关系必然有一个参照表,例如:

ThinkPHP系统就会自动定位到users表了。

  • 有一个员工档案管理系统项目,这个项目要包括下面的一些数据表:基本信息表、员工档案表、部门表、项目组表、银行卡表(用来记录员工的银行卡资料)。

  • 这些数据表之间存在一定的关联关系,我们以员工基本信息表为参照来分析和其他表之间的关联:

  • 每个员工必然有对应的员工档案资料,所以属于HAS_ONE关联;

  • 每个员工必须属于某个部门,所以属于BELONGS_TO关联;

  • 每个员工可以有多个银行卡,但是每张银行卡只可能属于一个员工,因此属于HAS_MANY关联;

  • 每个员工可以同时在多个项目组,每个项目组同时有多个员工,因此属于MANY_TO_MANY关联;

  • 分析清楚数据表之前的关联关系后,我们才可以进行关联定义和关联操作。

第二种情况时,如果你的模型类没有按照系统规范来命名,比如说不小心命名为UserModel,这种情况下可以同时指定表前缀和表明,比如:

  1. 关联定义

    ThinkPHP可以很轻松的完成数据表的关联CURD操作,目前支持的关联关系包括下面四种:

    HAS_ONEBELONGS_TOHAS_MANYMANY_TO_MANY

protected $tablePrefix = '';protected $tableName = 'users';
一个模型根据业务模型的复杂程度可以同时定义多个关联,不受限制,所有的关联定义都统一在模型类的 $_link 成员变量里面定义,并且可以支持动态定义。要支持关联操作,模型类必须继承Think\Model\RelationModel类,关联定义的格式是: 

namespace Home\Model; 

use Think\Model\RelationModel; 

class UserModel extends RelationModel{ 

 protected $_link = array( 


'关联1'
=> array( 


'关联属性1' => '定义',



'关联属性N' => '定义',


 ), 


'关联2'
=> array( 


'关联属性1' => '定义',



'关联属性N' => '定义',


 ), 


'关联3' => HAS_ONE, // 快捷定义 

 ... 

 ); 

} 

下面我们首先来分析下各个关联方式的定义: 

或者你直接指定trueTableName:

  1. HAS_ONE

    HAS_ONE关联表示当前模型拥有一个子对象,例如,每个员工都有一个人事档案。我们可以建立一个用户模型UserModel,并且添加如下关联定义:

    namespace HomeModel;

    use ThinkModelRelationModel;

    class UserModel extends RelationModel{

    protected $_link = array(

    'Profile'=> self::HAS_ONE,

    );

    }

    上面是最简单的方式,表示其遵循了系统内置的数据库规范,完整的定义方式是:

    namespace HomeModel;

    use ThinkModelRelationModel;

    class UserModel extends RelationModel{

    protected $_link = array(

    'Profile'=>array(

    'mapping_type' => self::HAS_ONE,

    'class_name' => 'Profile',

protected $trueTableName = 'users';

// 定义更多的关联属性 

 …… 

 ), 

 ); 

} 

关联HAS_ONE支持的关联属性有: 

**mapping_type :关联类型** 

这个在HAS_ONE 关联里面必须使用HAS_ONE 常量定义。 

**class_name :要关联的模型类名** 

例如,class_name 定义为Profile的话则表示和另外的Profile模型类关联,这个Profile模型类是无需定义的,系统会自动定位到相关的数据表进行关联。 

**mapping_name :关联的映射名称,用于获取数据用** 

该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。如果mapping_name没有定义的话,会取class_name的定义作为mapping_name。如果class_name也没有定义,则以数组的索引作为mapping_name。


**foreign_key :
关联的外键名称** 

外键的默认规则是当前数据对象名称_id,例如: UserModel对应的可能是表think_user (注意:think只是一个表前缀,可以随意配置) 那么think_user表的外键默认为 user_id,如果不是,就必须在定义关联的时候显式定义 foreign_key 。


**condition :
关联条件** 

关联查询的时候会自动带上外键的值,如果有额外的查询条件,可以通过定义关联的condition属性。 

**mapping_fields :
关联要查询的字段** 

默认情况下,关联查询的关联数据是关联表的全部字段,如果只是需要查询个别字段,可以定义关联的mapping_fields属性。 

**as_fields :直接把关联的字段值映射成数据对象中的某个字段** 

这个特性是ONE_TO_ONE 关联特有的,可以直接把关联数据映射到数据对象中,而不是作为一个关联数据。当关联数据的字段名和当前数据对象的字段名称有冲突时,还可以使用映射定义。 

既然模型通常是用来操作数据表,那么我们来看看模型的基本CURD:

  1. BELONGS_TO

    Belongs_to 关联表示当前模型从属于另外一个父对象,例如每个用户都属于一个部门。我们可以做如下关联定义。

    'Dept' => self::BELONGS_TO

    完整方式定义为:

    'Dept' => array(

    'mapping_type' => self::BELONGS_TO,

    'class_name' => 'Dept',

    'foreign_key' => 'userId',

    'mapping_name' => 'dept',

注:为了方便演示,我们在UserController中定义一个testDemo()方法用于演示

// 定义更多的关联属性 

 …… 

), 

关联BELONGS_TO定义支持的关联属性有: 

<table>
<tbody>
<tr class="odd">
<td><p><strong>属性</strong></p></td>
<td><p><strong>描述</strong></p></td>
</tr>
<tr class="even">
<td><p>class_name</p></td>
<td><p>要关联的模型类名</p></td>
</tr>
<tr class="odd">
<td><p>mapping_name</p></td>
<td><p>关联的映射名称,用于获取数据用 该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。</p></td>
</tr>
<tr class="even">
<td><p>foreign_key</p></td>
<td><p>关联的外键名称</p></td>
</tr>
<tr class="odd">
<td><p>mapping_fields</p></td>
<td><p>关联要查询的字段</p></td>
</tr>
<tr class="even">
<td><p>condition</p></td>
<td><p>关联条件</p></td>
</tr>
<tr class="odd">
<td><p>parent_key</p></td>
<td><p>自引用关联的关联字段 默认为parent_id 自引用关联是一种比较特殊的关联,也就是关联表就是当前表。</p></td>
</tr>
<tr class="even">
<td><p>as_fields</p></td>
<td><p>直接把关联的字段值映射成数据对象中的某个字段</p></td>
</tr>
</tbody>
</table>
public function testDemo() { }
  1. HAS_MANY

    HAS_MANY 关联表示当前模型拥有多个子对象,例如每个用户有多篇文章,我们可以这样来定义:

    'Article' => self::HAS_MANY

    完整定义方式为:

    'Article' => array(

    'mapping_type' => self::HAS_MANY,

    'class_name' => 'Article',

    'foreign_key' => 'userId',

    'mapping_name' => 'articles',

    'mapping_order' => 'create_time desc',

以下的代码将会一段一段在这个方法里演示,你可以通过访问

// 定义更多的关联属性 

 …… 

), 

关联HAS_MANY定义支持的关联属性有: 

<table>
<tbody>
<tr class="odd">
<td><p><strong>属性</strong></p></td>
<td><p><strong>描述</strong></p></td>
</tr>
<tr class="even">
<td><p>class_name</p></td>
<td><p>要关联的模型类名</p></td>
</tr>
<tr class="odd">
<td><p>mapping_name</p></td>
<td><p>关联的映射名称,用于获取数据用 该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。</p></td>
</tr>
<tr class="even">
<td><p>foreign_key</p></td>
<td><p>关联的外键名称</p></td>
</tr>
<tr class="odd">
<td><p>parent_key</p></td>
<td><p>自引用关联的关联字段 默认为parent_id</p></td>
</tr>
<tr class="even">
<td><p>condition</p></td>
<td><p>关联条件 关联查询的时候会自动带上外键的值,如果有额外的查询条件,可以通过定义关联的condition属性。</p></td>
</tr>
<tr class="odd">
<td><p>mapping_fields</p></td>
<td><p>关联要查询的字段 默认情况下,关联查询的关联数据是关联表的全部字段,如果只是需要查询个别字段,可以定义关联的mapping_fields属性。</p></td>
</tr>
<tr class="even">
<td><p>mapping_limit</p></td>
<td><p>关联要返回的记录数目</p></td>
</tr>
<tr class="odd">
<td><p>mapping_order</p></td>
<td><p>关联查询的排序</p></td>
</tr>
</tbody>
</table>

外键的默认规则是当前数据对象名称_id,例如:UserModel对应的可能是表think_user (注意:think只是一个表前缀,可以随意配置) 那么think_user表的外键默认为 user_id,如果不是,就必须在定义关联的时候定义 foreign_key 。

添加纪录

  1. MANY_TO_MANY
$user = M;$data['username'] = 'ThinkPHP';$data['email'] = 'ThinkPHP@gmail.com';$user->create;$record = $user->add;
MANY_TO_MANY 关联表示当前模型可以属于多个对象,而父对象则可能包含有多个子对象,通常两者之间需要一个中间表类约束和关联。例如每个用户可以属于多个组,每个组可以有多个用户: 

'Group' =&gt; self::MANY_TO_MANY 

完整定义方式为: 

'Group' =&gt; array( 

 'mapping_type' =&gt; self::MANY_TO_MANY, 

 'class_name' =&gt; 'Group', 

 'mapping_name' =&gt; 'groups', 

 'foreign_key' =&gt; 'userId', 

 'relation_foreign_key' =&gt; 'groupId', 


'relation_table' =&gt; 'think_group_user' //此处应显式定义中间表名称,且不能使用C函数读取表前缀 

 ) 

MANY_TO_MANY支持的关联属性定义有: 

<table>
<tbody>
<tr class="odd">
<td><p><strong>属性</strong></p></td>
<td><p><strong>描述</strong></p></td>
</tr>
<tr class="even">
<td><p>class_name</p></td>
<td><p>要关联的模型类名</p></td>
</tr>
<tr class="odd">
<td><p>mapping_name</p></td>
<td><p>关联的映射名称,用于获取数据用 该名称不要和当前模型的字段有重复,否则会导致关联数据获取的冲突。</p></td>
</tr>
<tr class="even">
<td><p>foreign_key</p></td>
<td><p>关联的外键名称 外键的默认规则是当前数据对象名称_id</p></td>
</tr>
<tr class="odd">
<td><p>relation_foreign_key</p></td>
<td><p>关联表的外键名称 默认的关联表的外键名称是表名_id</p></td>
</tr>
<tr class="even">
<td><p>mapping_limit</p></td>
<td><p>关联要返回的记录数目</p></td>
</tr>
<tr class="odd">
<td><p>mapping_order</p></td>
<td><p>关联查询的排序</p></td>
</tr>
<tr class="even">
<td><p>relation_table</p></td>
<td><p>多对多的中间关联表名称</p></td>
</tr>
</tbody>
</table>

多对多的中间表默认表规则是:**数据表前缀****_关联操作的主表名_关联表名** 

如果think_user 和
think_group 存在一个对应的中间表,默认的表名应该是 如果是由group来操作关联表,中间表应该是 think_group_user,如果是从user表来操作,那么应该是think_user_group,也就是说,多对多关联的设置,必须有一个Model类里面需要显式定义中间表,否则双向操作会出错。 中间表无需另外的id主键(但是这并不影响中间表的操作),通常只是由 user_id 和
group_id 构成。 默认会通过当前模型的getRelationTableName方法来自动获取,如果当前模型是User,关联模型是Group,那么关联表的名称也就是使用 user_group这样的格式,如果不是默认规则,需要指定relation_table属性。 

**3.2.2****版本**开始,relation_table定义支持简化写法,例如: 

'relation_table'=&gt;'__USER_GROUP__'

add()返回的是插入数据的id,对于不存在的表字段,add()方法会自动过滤。

  1. 关联查询

    由于性能问题,新版取消了自动关联查询机制,而统一使用relation方法进行关联操作,relation方法不但可以启用关联还可以控制局部关联操作,实现了关联操作一切尽在掌握之中。

    $User = D("User");

    $user = $User->relation(true)->find(1);

    输出$user结果可能是类似于下面的数据:

    array(

    'id' => 1,

    'account' => 'ThinkPHP',

    'password' => '123456',

    'Profile' => array(

    'email' => 'liu21st@gmail.com',

读取纪录

'nickname' =&gt; '流年',


 ), 

 ) 

我们可以看到,用户的关联数据已经被映射到数据对象的属性里面了。其中Profile就是关联定义的mapping_name属性。 

如果我们按照下面的方式定义了as_fields属性的话, 

protected $_link = array( 

 'Profile'=&gt;array( 

 'mapping_type' =&gt; self::HAS_ONE, 

 'class_name' =&gt; 'Profile', 

 'foreign_key' =&gt; 'userId', 

 'as_fields' =&gt; 'email,nickname', 

 ), 

 ); 

查询的结果就变成了下面的结果 

array( 

 'id' =&gt; 1, 

 'account' =&gt; 'ThinkPHP', 

 'password' =&gt; 'name', 

 'email' =&gt; 'liu21st@gmail.com', 


'nickname' =&gt; '流年',


 ) 

email和nickname两个字段已经作为user数据对象的字段来显示了。 

如果关联数据的字段名和当前数据对象的字段有冲突的话,怎么解决呢? 

我们可以用下面的方式来变化下定义: 

'as_fields' =&gt; 'email,nickname:username', 

表示关联表的nickname字段映射成当前数据对象的username字段。 

默认会把所有定义的关联数据都查询出来,有时候我们并不希望这样,就可以给relation方法传入参数来控制要关联查询的。 

$User =
D("User"); 

$user =
$User-&gt;relation('Profile')-&gt;find(1); 

关联查询一样可以支持select方法,如果要查询多个数据,并同时获取相应的关联数据,可以改成: 

$User = D("User"); 

$list = $User-&gt;relation(true)-&gt;Select(); 

如果希望在完成的查询基础之上 再进行关联数据的查询,可以使用 

$User = D("User"); 

$user = $User-&gt;find(1); 

// 表示对当前查询的数据对象进行关联数据获取 

$profile = $User-&gt;relationGet("Profile"); 

事实上,除了当前的参考模型User外,其他的关联模型是不需要创建的。 

在ThinkPHP中读取数据的方式很多,通常分为读取数据、读取数据集和读取字段值

  1. 关联操作

    除了关联查询外,系统也支持关联数据的自动写入、更新和删除

  2. 关联写入

    $User = D("User");

    $data = array();

    $data["account"] = "ThinkPHP";

    $data["password"] = "123456";

    $data["Profile"] = array(

    'email' =>'liu21st@gmail.com',

$user = M;$record = $user->where('username="ThinkPHP"')->find;

$user = M;$record = $user->where->getField;dump;
'nickname' =&gt;'流年',


); 

$result =
$User-&gt;relation(true)-&gt;add($data); 

这样就会自动写入关联的Profile数据。 

同样,可以使用参数来控制要关联写入的数据: 

$result = $User-&gt;relation("Profile")-&gt;add($data); 

当MANY_TO_MANY时,不建议使用关联插入。 

默认情况下,当只有一个字段的时候,返回满足条件的数据表中的该字段的第一行的值.如果getField()传入多个字段,返回值将是一个关联数组:

  1. 关联更新

    数据的关联更新和关联写入类似

    $User = D("User");

    $data["account"] = "ThinkPHP";

    $data["password"] = "123456";

    $data["Profile"] = array(

    'email' =>'liu21st@gmail.com',

$user = M;$record = $user->getField;dump;
'nickname' =&gt;'流年',


); 

$result =
$User-&gt; relation(true)-&gt;where(array('id'=&gt;3))-&gt;save($data); 

Relation(true)会关联保存User模型定义的所有关联数据,如果只需要关联保存部分数据,可以使用: 

$result = $User-&gt;relation("Profile")-&gt;save($data); 

这样就只会同时更新关联的Profile数据。 

关联保存的规则: 

**HAS_ONE**:
关联数据的更新直接赋值 

**HAS_MANY**:
的关联数据如果传入主键的值 则表示更新 否则就表示新增 

**MANY_TO_MANY**:
的数据更新是删除之前的数据后重新写入 

这个数组总是以传入的第一个第一个字段为键值的。如果修改为:

  1. 关联删除

    //删除用户ID为3的记录的同时删除关联数据

    $result = $User->relation(true)->delete("3");

    // 如果只需要关联删除部分数据,可以使用

    $result = $User->relation("Profile")->delete("3");

     

    2017/6/29 4:55 PM

$user = M;$record = $user->getField;dump;

将上面的两次代码分别放到testDemo(),你就会看到不一样的结果集。

用save()方法更新数据

$user = M;$data['username'] = 'ThinkPHPSave';$data['email'] = 'ThinkPHPSave@outlook.com';$record = $user->where;dump;

这里的$record返回的事1,表示成功更改。

本文由美高梅平台下载发布于美高梅平台下载,转载请注明出处:模型定义, // 这要会更好

关键词:

json是一种数据传输格式,1、一维数组 考虑php数

$arr=array;$str=json_encode;echo "";function add{alert;//array就是$str数组} json_encode():编码,生成一个json字符串json_decode():一个解...

详细>>

这就涉及到在shell命令下如何给php传参的问题,

通常PHP都做http方式请求了,可以使用GET orPOST方式接收参数,有些时候需要在shell命令下把PHP当作脚本执行,比如定时...

详细>>

是否记录profile可以由程序控制

xhprof是facebook开源出来的一个php性能测试工具,也可以称之为profile工具,这个词不知道怎么翻译才比较达意。跟之前...

详细>>

我们可以用php来开发Shell程序

1.基础知识 1.1 什么是Shell编程? 在 Unix 中,shell可不是简单的命令解释器,而是一个全功能的编程环境。Shell是操作系...

详细>>