# 关系型 Active Record #
https://www.yiichina.com/doc/guide/1.1/database.arr
BELONGS_TO(属于): 如果表 A 和 B 之间的关系是一对多,则 表 B 属于 表 A (例如 Post 属于 User);
HAS_MANY(有多个): 如果表 A 和 B 之间的关系是一对多,则 A 有多个 B (例如 User 有多个 Post);
HAS_ONE(有一个): 这是 HAS_MANY 的一个特例,A 最多有一个 B (例如 User 最多有一个 Profile);
MANY_MANY: 这个对应于数据库中的 多对多 关系。 由于多数 DBMS 不直接支持 多对多 关系,因此需要有一个关联表将 多对多 关系分割为 一对多 关系。 在我们的示例数据结构中,tbl_post_category 就是用于此目的的。在 AR 术语中,我们可以解释 MANY_MANY 为 BELONGS_TO 和 HAS_MANY 的组合。 例如,Post 属于多个(belongs to many) Category ,Category 有多个(has many) Post.
## 项目示例
D:\wamp\www\weike.test\weiketest\protected\models\weike\wkeTeachingV3.php
```
public function tableName()
{
return WK::DBweike.'.tbTeachingV3';
}
public function relations()
{
return array(
'prepare' => array(self::BELONGS_TO, 'wkePrepare', 'fdPrepareID'),
'class'=>array(self::BELONGS_TO,'wkeClass','fdClassID') ,//by liupf 2016/7/9
'record'=>array(self::HAS_MANY,'wkeTeachingV3Student','fdTeachingV3ID'),//by liupf 2016/9/28
'content'=>array(self::BELONGS_TO,'Content','fdPrepareID'),//by liupf 2016/9/28
'user'=>array(self::BELONGS_TO,'User','fdTeacherID'),//by liupf 2016/10/19
'operations' => array(self::HAS_MANY,'wkeTeachingV3Operation','fdTeachingV3ID') ,
'schoolMap'=>array(self::HAS_ONE,'SchoolMap','','on'=>'t.fdTeacherID = schoolMap.fdUserID'),
);
}
```
D:\wamp\www\weike.test\weiketest\protected\models\weike\wkePrepare.php
```
public function tableName()
{
return WK::DBweike . '.tbPrepare';
}
public function relations()
{
return array(
'user' => array(self::BELONGS_TO, 'User', 'fdTeacherID'),
'prepareItems' => array(self::HAS_MANY, 'wkePrepareItem', 'fdPrepareID'),
'itemCnts' => array(self::HAS_MANY, 'wkePrepareItemContent',array('id'=>'fdPrepareItemID'),'through'=>'prepareItems'),
'bookTag' => array(self::BELONGS_TO, 'Tag', 'fdTextbookID'),
'tag' => array(self::BELONGS_TO, 'Tag', 'fdTagID'),
'content' => array(self::BELONGS_TO, 'Content', 'fdContentID'),
'cntPreHw' => array(self::STAT, 'wkeAssignment', 'fdPrepareID',
'condition' => 't.fdType=' . WK::PREPARE_ITEM_TYPE_PREVIEW),
'cntAssHw' => array(self::STAT, 'wkeAssignment', 'fdPrepareID',
'condition' => 't.fdType=' . WK::PREPARE_ITEM_TYPE_ASSIGNMENT),
'cntTch' => array(self::STAT, 'wkeInClass', 'fdPrepareID'),
'groupMap' => array(self::HAS_MANY, 'wkePrepareGroupMap', 'fdPrepareID'),
'boards' => array(self::HAS_MANY, 'wkePrepareBoard', 'fdPrepareID'),
'ctnTagIndex' => array(self::HAS_MANY, 'wkeCtnTagIndex', '', 'on' => 't.fdContentID=ctnTagIndex.fdContentID'),
);
}
```
## 多对多关联模型
**D:\wamp\www\xue.test\xuetang\protected\models\service\User.php**
```
public function relations(){
'usercourse' => array(self::MANY_MANY, 'xtCourse', 'wkxuetang.tbCourseStudent(fdUserID, fdCourseID)'),
}
```
**D:\wamp\www\xue.test\xuetang\protected\modules\courseCenter\controllers\StuCourseController.php**
```
/**
* 获取当前用户的课程
*/
public function actionGetMyCourse()
{
$userId = RequestUtils::getNormalRequest('userId'); //19
if (!$userId) {
ResponseUtils::json(null, 1, 'fail');
}
$criteria = new CDbCriteria();
$criteria->with = ['usercourse'];
$criteria->addCondition("t.id=" . $userId);
$list = User::model()->findAll($criteria);
if ($list) {
ResponseUtils::json($list);
}
ResponseUtils::json(null, 1, 'fail');
}
```
### SQL
```
SELECT
`t`.`id` AS `t0_c0`,
`t`.`fdNumber` AS `t0_c1`,
`t`.`fdLogin` AS `t0_c2`,
`t`.`fdName` AS `t0_c3`,
`t`.`fdRealName` AS `t0_c4`,
`t`.`fdPassword` AS `t0_c5`,
`t`.`fdActive` AS `t0_c6`,
`t`.`fdQuestion` AS `t0_c7`,
`t`.`fdAnswer` AS `t0_c8`,
`t`.`fdPortrait` AS `t0_c9`,
`t`.`fdGender` AS `t0_c10`,
`t`.`fdApprove` AS `t0_c11`,
`t`.`fdApproverID` AS `t0_c12`,
`t`.`fdCreate` AS `t0_c13`,
`t`.`fdStatus` AS `t0_c14`,
`t`.`fdTypeID` AS `t0_c15`,
`t`.`fdCardID` AS `t0_c16`,
`t`.`fdPoints` AS `t0_c17`,
`t`.`fdMoney` AS `t0_c18`,
`t`.`fdCash` AS `t0_c19`,
`t`.`fdDisabled` AS `t0_c20`,
`t`.`fdShutup` AS `t0_c21`,
`t`.`fdExpired` AS `t0_c22`,
`t`.`fdRgType` AS `t0_c23`,
`t`.`fdVipType` AS `t0_c24`,
`t`.`fdOutsideUID` AS `t0_c25`,
`t`.`fdOutsideHost` AS `t0_c26`,
`t`.`fdIsXuetang` AS `t0_c27`,
`t`.`fdTeacherID` AS `t0_c28`,
`t`.`fdParentID` AS `t0_c29`,
`t`.`fdTeamType` AS `t0_c30`,
`t`.`fdOutsideUUID` AS `t0_c31`,
`usercourse`.`id` AS `t1_c0`,
`usercourse`.`fdUserID` AS `t1_c1`,
`usercourse`.`fdName` AS `t1_c2`,
`usercourse`.`fdCourseType` AS `t1_c3`,
`usercourse`.`fdSubjectID` AS `t1_c4`,
`usercourse`.`fdSchoolTypeID` AS `t1_c5`,
`usercourse`.`fdViewType` AS `t1_c6`,
`usercourse`.`fdDiff` AS `t1_c7`,
`usercourse`.`fdFee` AS `t1_c8`,
`usercourse`.`fdThumb` AS `t1_c9`,
`usercourse`.`fdVideo` AS `t1_c10`,
`usercourse`.`fdVideoThumb` AS `t1_c11`,
`usercourse`.`fdInfo` AS `t1_c12`,
`usercourse`.`fdStatus` AS `t1_c13`,
`usercourse`.`fdCreate` AS `t1_c14`,
`usercourse`.`fdUpdate` AS `t1_c15`
FROM
`wksvc`.`tbUser` `t`
LEFT OUTER JOIN `wkxuetang`.`tbCourseStudent` `usercourse_usercourse` ON (
`t`.`id` = `usercourse_usercourse`.`fdUserID`
)
LEFT OUTER JOIN `wkxuetang`.`tbCourse` `usercourse` ON (
`usercourse`.`id` = `usercourse_usercourse`.`fdCourseID`
)
WHERE
(t.id = 19)
```
### 图示
![](./img/2018-11-21_180305.png)
![](./img/2018-11-21_180346.png)
- 说明
- 开发任务
- 星课-真光
- 课表
- Excel Down
- 调课
- 课表修改
- 课表代码分析
- 课堂
- 课堂:应用商店通信管理协议
- 教师账号强制绑定手机或邮箱
- 强制绑定手机和修改密码的规则
- 学堂
- 课程学习:讨论功能
- 后台:课程讨论管理
- 课程直播接口
- 学习统计功能(旧版)
- 学习统计功能(新版)
- 同步课程统计功能
- 同步课程编辑-新增视频
- 第三方接口
- 学科网
- 安徽第三方
- 大赛
- 管控系统
- 日志管理
- 设备日志
- 平板接口
- 渝教
- 教学总结
- 空白目录
- Yii 1.1
- 学堂架构
- Yii 1.1一些方法的解读
- MVCS结构
- 基础使用语法
- 创建1个新模块
- 关联模型
- CDbCriteria
- 学生-课堂记录
- 学生端页面展示
- 教师端页面展示
- 编辑课程文档
- SQL
- 课堂项目运行入口
- 上传资源示意图
- 行为
- PHPStorm
- 源码阅读
- 会诊答卷页面
- 考点练习
- 资源首页
- 同步课程
- 同步课程:章节信息
- 升学复习
- 统计图-范例
- 模块
- 非法词
- 服务层
- MongoDB类
- 学堂作答记录从Mongo新集合获取数据
- MongoYii
- 错题集
- 小技巧
- 完善资料
- 邮件发送
- K12
- JSpang视频课程
- MongoDB
- 创业
- 项目
- 包包