laravel belongsToMany和hasMany用法解析

场景

coding中经常用到了,两者有非常明显的差异,记录下来 方面以后翻阅

分析(不同)

1. 使用场景不同
    .   hasMany 应用在One To Many的场景中
        问题Question Model和答案Answer Model,一个问题下面可以有多个答案,但是一个答案只可以对应一个问题。
    . belongsToMany应用在Many to Many的场景
      话题Topic Model和问题Question Model            

2.   对应的paired的relationship不同
    .  hasMany对应的relatioship是 belongsTo 
        Question Model  and Answer Model 
    /**
     * Question Model
     * 定义问题答案的relationship (一对多)
     */
    public function answers()
    {
        return $this->hasMany(Answer::class, 'question_id', 'id');
    }
    /** 
     * Question Model
     * 话题多对多关系
     * @return \Illuminate\Database\Eloquent\Relations\BelongsToMany
     */
    public function topic()
    {
        return $this->belongsToMany(Topic::class)->withTimestamps();
    }
    /**
     * Answer Model一对多
     * relationship
     * @return \Illuminate\Database\Eloquent\Relations\BelongsTo
     */
    public function question()
    {
        return $this->belongsTo(Question::class);
    }
    .  belongsToMany 对应的relationship是belongsToMany 
       Question Model and Topic Model

3.   表的数据结构不同
      .   hasMany要求数据表的关联关系存储一个Model上面, 因为是一对多的关系 所以这种模式是可以的
          Question Model  and Answer Model   存在 Answer.question_id 但是不需要Question.answer_id,也不需要pivot table
      .    belongsToMany 必须使用pivot table,里面存储两者的关联关系
        Question Model And Topic Model  topic_id question_id 放在自身的Model中无法实现多对多的关系, 需要pivot table 
        存储references
CREATE TABLE `questions` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `user_id` int(10) unsigned NOT NULL,
  `title` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '标题',
  `body` text COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '问题内容',
  `flowers_count` int(11) NOT NULL DEFAULT '0' COMMENT '关注的数目',
  `comments_count` int(11) NOT NULL DEFAULT '1' COMMENT '评论的数目',
  `close_comment` varchar(8) COLLATE utf8mb4_unicode_ci NOT NULL DEFAULT 'F' COMMENT '评论的状态 F可以评论 T关闭评论',
  `is_hidden` varchar(8) COLLATE utf8mb4_unicode_ci NOT NULL DEFAULT 'F' COMMENT '问题状态  F正常 T隐藏删除',
  `created_at` timestamp NULL DEFAULT NULL,
  `updated_at` timestamp NULL DEFAULT NULL,
  `answers_count` int(10) unsigned NOT NULL DEFAULT '0' COMMENT '回答的数量',
  PRIMARY KEY (`id`),
  KEY `questions_user_id_foreign` (`user_id`),
  CONSTRAINT `questions_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=27 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;

CREATE TABLE `answers` (
  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NOT NULL COMMENT '回答者',
  `question_id` int(11) NOT NULL COMMENT '问题ID',
  `body` text COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '回答内容',
  `votes_count` int(11) NOT NULL DEFAULT '0' COMMENT '点赞总数',
  `comments_count` int(11) NOT NULL DEFAULT '0' COMMENT '评论总数',
  `is_hidden` varchar(8) COLLATE utf8mb4_unicode_ci NOT NULL DEFAULT 'F' COMMENT '是否隐藏起来 F显示 T隐藏',
  `close_comment` varchar(8) COLLATE utf8mb4_unicode_ci NOT NULL DEFAULT 'F' COMMENT '是否关闭评论 F允许评论 T关闭评论',
  `created_at` timestamp NULL DEFAULT NULL,
  `updated_at` timestamp NULL DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `answers_user_id_index` (`user_id`),
  KEY `answers_question_id_index` (`question_id`)
) ENGINE=InnoDB AUTO_INCREMENT=10 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci

你可能感兴趣的:(laravel)