<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                企業??AI智能體構建引擎,智能編排和調試,一鍵部署,支持知識庫和私有化部署方案 廣告
                # 關聯模型 [上一頁](# "上一頁")[下一頁](# "下一頁") ### 關聯關系 通常我們所說的關聯關系包括下面三種: 一對一關聯 :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關聯; 分析清楚數據表之前的關聯關系后,我們才可以進行關聯定義和關聯操作。 ### 關聯定義 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支持的關聯屬性有: <table border="0" cellspacing="1" cellpadding="0"><tr><td><b>mapping_type</b> </td><td width="450">關聯類型,這個在HAS_ONE 關聯里面必須使用HAS_ONE 常量定義。</td></tr><tr><td><b>class_name</b> </td><td>要關聯的模型類名<br/>例如,class_name 定義為Profile的話則表示和另外的Profile模型類關聯,這個Profile模型類是無需定義的,系統會自動定位到相關的數據表進行關聯。</td></tr><tr><td><b>mapping_name</b> </td><td>關聯的映射名稱,用于獲取數據用<br/>該名稱不要和當前模型的字段有重復,否則會導致關聯數據獲取的沖突。如果mapping_name沒有定義的話,會取class_name的定義作為mapping_name。如果class_name也沒有定義,則以數組的索引作為mapping_name。</td></tr><tr><td><b>foreign_key</b> </td><td>關聯的外鍵名稱<br/>外鍵的默認規則是當前數據對象名稱_id,例如:<br/>UserModel對應的可能是表think_user (注意:think只是一個表前綴,可以隨意配置)<br/>那么think_user表的外鍵默認為 user_id,如果不是,就必須在定義關聯的時候顯式定義 foreign_key 。</td></tr><tr><td><b>condition</b> </td><td>關聯條件<br/>關聯查詢的時候會自動帶上外鍵的值,如果有額外的查詢條件,可以通過定義關聯的condition屬性。</td></tr><tr><td><b>mapping_fields</b> </td><td>關聯要查詢的字段<br/>默認情況下,關聯查詢的關聯數據是關聯表的全部字段,如果只是需要查詢個別字段,可以定義關聯的mapping_fields屬性。</td></tr><tr><td><b>as_fields</b></td><td>直接把關聯的字段值映射成數據對象中的某個字段<br/>這個特性是ONE_TO_ONE 關聯特有的,可以直接把關聯數據映射到數據對象中,而不是作為一個關聯數據。當關聯數據的字段名和當前數據對象的字段名稱有沖突時,還可以使用映射定義。</td></tr></table> **BELONGS_TO** Belongs_to 關聯表示當前模型從屬于另外一個父對象,例如每個用戶都屬于一個部門。我們可以做如下關聯定義。`?'Dept'=>?BELONGS_TO`完整方式定義為: `'Dept'=>?array(?? ?????'mapping_type'=>BELONGS_TO, ??????????'class_name'=>'Dept', ??????????'foreign_key'=>'userId', ??????????'mapping_name'=>'dept', ???????????//?定義更多的關聯屬性 ????????…… ),`關聯BELONGS_TO定義支持的關聯屬性有: <table border="0" cellspacing="1" cellpadding="0"><tr><td>class_name</td><td> 要關聯的模型類名</td></tr><tr><td>mapping_name </td><td>關聯的映射名稱,用于獲取數據用<br/>該名稱不要和當前模型的字段有重復,否則會導致關聯數據獲取的沖突。</td></tr><tr><td>foreign_key </td><td>關聯的外鍵名稱</td></tr><tr><td>mapping_fields</td><td> 關聯要查詢的字段</td></tr><tr><td>condition</td><td> 關聯條件</td></tr><tr><td>parent_key</td><td> 自引用關聯的關聯字段<br/>默認為parent_id <br/>自引用關聯是一種比較特殊的關聯,也就是關聯表就是當前表。</td></tr><tr><td>as_fields</td><td>直接把關聯的字段值映射成數據對象中的某個字段</td></tr></table> **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定義支持的關聯屬性有: <table border="0" cellspacing="1" cellpadding="0"><tr><td>class_name</td><td>要關聯的模型類名</td></tr><tr><td>mapping_name</td><td> 關聯的映射名稱,用于獲取數據用<br/>該名稱不要和當前模型的字段有重復,否則會導致關聯數據獲取的沖突。</td></tr><tr><td>foreign_key</td><td> 關聯的外鍵名稱<br/>外鍵的默認規則是當前數據對象名稱_id,例如:<br/>UserModel對應的可能是表think_user (注意:think只是一個表前綴,可以隨意配置)<br/>那么think_user表的外鍵默認為 user_id,如果不是,就必須在定義關聯的時候定義 foreign_key 。</td></tr><tr><td>parent_key</td><td> 自引用關聯的關聯字段<br/>默認為parent_id </td></tr><tr><td>condition</td><td> 關聯條件<br/>關聯查詢的時候會自動帶上外鍵的值,如果有額外的查詢條件,可以通過定義關聯的condition屬性。</td></tr><tr><td>mapping_fields</td><td> 關聯要查詢的字段<br/>默認情況下,關聯查詢的關聯數據是關聯表的全部字段,如果只是需要查詢個別字段,可以定義關聯的mapping_fields屬性。</td></tr><tr><td>mapping_limit</td><td> 關聯要返回的記錄數目</td></tr><tr><td>mapping_order</td><td> 關聯查詢的排序</td></tr></table> **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支持的關聯屬性定義有: <table border="0" cellspacing="1" cellpadding="0"><tr><td>class_name</td><td>要關聯的模型類名</td></tr><tr><td>mapping_name</td><td> 關聯的映射名稱,用于獲取數據用<br/>該名稱不要和當前模型的字段有重復,否則會導致關聯數據獲取的沖突。</td></tr><tr><td>foreign_key</td><td> 關聯的外鍵名稱<br/>外鍵的默認規則是當前數據對象名稱_id</td></tr><tr><td>relation_foreign_key</td><td> 關聯表的外鍵名稱<br/>默認的關聯表的外鍵名稱是表名_id</td></tr><tr><td>mapping_limit</td><td> 關聯要返回的記錄數目</td></tr><tr><td>mapping_order</td><td> 關聯查詢的排序</td></tr><tr><td>relation_table</td><td>多對多的中間關聯表名稱</td></tr></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屬性。 ### 關聯查詢 由于性能問題,新版取消了自動關聯查詢機制,而統一使用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外,其他的關聯模型是不需要創建的。 ### 關聯操作 除了關聯查詢外,系統也支持關聯數據的自動寫入、更新和刪除 **關聯寫入**`$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");` [上一頁](# "上一頁")[下一頁](# "下一頁")
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看