Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/238.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/58.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 子查询未返回预期结果_Php_Mysql_Codeigniter_Join_Subquery - Fatal编程技术网

Php 子查询未返回预期结果

Php 子查询未返回预期结果,php,mysql,codeigniter,join,subquery,Php,Mysql,Codeigniter,Join,Subquery,这是我为获得用户选择的计划而编写的查询。但这将返回usersubscription表中的记录,即使该用户未订阅(如果该用户对应的表中没有记录) 下面我分享所有表格的结构 CREATE TABLE IF NOT EXISTS `subscribed_videos` ( `id` int(11) NOT NULL AUTO_INCREMENT, `plan_id` int(11) NOT NULL, `videoid` int(11) NOT NULL, PRIMARY KEY (`

这是我为获得用户选择的计划而编写的查询。但这将返回usersubscription表中的记录,即使该用户未订阅(如果该用户对应的表中没有记录)

下面我分享所有表格的结构

CREATE TABLE IF NOT EXISTS `subscribed_videos` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `plan_id` int(11) NOT NULL,
  `videoid` int(11) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB  DEFAULT CHARSET=latin1 AUTO_INCREMENT=26 ;

INSERT INTO `subscribed_videos` (`id`, `plan_id`, `videoid`) VALUES
(7, 2, 1),
(8, 2, 2),
(14, 1, 3),
(15, 1, 4),
(16, 1, 5),
(17, 1, 21),
(18, 1, 28),
(19, 1, 2),
(20, 3, 4),
(21, 3, 6),
(24, 5, 25),
(25, 6, 5);

CREATE TABLE IF NOT EXISTS `subscription_groups` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `plan_id` int(11) NOT NULL,
  `assosiated_plan_id` int(11) NOT NULL,
  `added_on` int(11) NOT NULL,
  PRIMARY KEY (`id`)
);


INSERT INTO `subscription_groups` (`id`, `plan_id`, `assosiated_plan_id`, `added_on`) VALUES
(1, 1, 1, 0),
(2, 2, 2, 0),
(3, 3, 3, 0),
(4, 4, 1, 0),
(5, 4, 2, 0),
(6, 4, 3, 0),
(12, 5, 5, 0),
(13, 5, 1, 0),
(14, 5, 2, 0),
(15, 6, 1, 0);

CREATE TABLE IF NOT EXISTS `subscription_plans` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `plan` varchar(256) NOT NULL,
  `days_limit` int(11) NOT NULL,
  `added_on` int(11) NOT NULL,
  `status` int(11) NOT NULL,
  `rate` decimal(6,2) NOT NULL,
  PRIMARY KEY (`id`)
);



INSERT INTO `subscription_plans` (`id`, `plan`, `days_limit`, `added_on`, `status`, `rate`) VALUES
(1, 'PlanA', 15, 1398249706, 1, 150.00),
(2, 'PlanB', 15, 1398249679, 1, 100.00),
(3, 'PlanC', 15, 1398249747, 1, 100.00),
(4, 'PlanD', 10, 1398249771, 1, 500.00),
(5, 'PlanE', 15, 1398250104, 1, 200.00),
(6, 'Plan R1', 20, 1398250104, 1, 200.00);


CREATE TABLE IF NOT EXISTS `usersubscription` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NOT NULL,
  `plan_id` int(11) NOT NULL,
  `subscribed_on` int(11) NOT NULL,
  PRIMARY KEY (`id`)
);



INSERT INTO `usersubscription` (`id`, `user_id`, `plan_id`, `subscribed_on`) VALUES
(1, 1, 1, 1399091458);
内容:

SELECT * FROM subscribed_videos; 
+----+---------+---------+
| id | plan_id | videoid |
+----+---------+---------+
|  7 |       2 |       1 |
|  8 |       2 |       2 |
| 14 |       1 |       3 |
| 15 |       1 |       4 |
| 16 |       1 |       5 |
| 17 |       1 |      21 |
| 18 |       1 |      28 |
| 19 |       1 |       2 |
| 20 |       3 |       4 |
| 21 |       3 |       6 |
| 24 |       5 |      25 |
| 25 |       6 |       5 |
+----+---------+---------+

SELECT * FROM subscription_groups; 
+----+---------+--------------------+----------+
| id | plan_id | assosiated_plan_id | added_on |
+----+---------+--------------------+----------+
|  1 |       1 |                  1 |        0 |
|  2 |       2 |                  2 |        0 |
|  3 |       3 |                  3 |        0 |
|  4 |       4 |                  1 |        0 |
|  5 |       4 |                  2 |        0 |
|  6 |       4 |                  3 |        0 |
| 12 |       5 |                  5 |        0 |
| 13 |       5 |                  1 |        0 |
| 14 |       5 |                  2 |        0 |
| 15 |       6 |                  1 |        0 |
+----+---------+--------------------+----------+

SELECT * FROM subscription_plans;
+----+---------+------------+------------+--------+--------+
| id | plan    | days_limit | added_on   | status | rate   |
+----+---------+------------+------------+--------+--------+
|  1 | PlanA   |         15 | 1398249706 |      1 | 150.00 |
|  2 | PlanB   |         15 | 1398249679 |      1 | 100.00 |
|  3 | PlanC   |         15 | 1398249747 |      1 | 100.00 |
|  4 | PlanD   |         10 | 1398249771 |      1 | 500.00 |
|  5 | PlanE   |         15 | 1398250104 |      1 | 200.00 |
|  6 | Plan R1 |         20 | 1398250104 |      1 | 200.00 |
+----+---------+------------+------------+--------+--------+

 SELECT * FROM usersubscription
+----+---------+---------+---------------+
| id | user_id | plan_id | subscribed_on |
+----+---------+---------+---------------+
|  1 |       1 |       1 |    1399091458 |
+----+---------+---------+---------------+
相同的小提琴:

如果用户已经订阅了所选视频的计划,我希望结果是这样的,否则查询将返回空记录:

id
---
1
另外,对于使用查询本身的用户,如何仅在计划未过期的情况下返回记录。也就是说,当用户购买计划时,它将被输入到usersubscription表中。subscribed_on字段将包含购买它的php unix
time()
。因此,我只想在这个查询中获得与用户和视频相对应的计划,这些计划没有过期。到期日存储为订阅计划表(例如:15)的天数限制字段中的天数

有人能帮我找到一个合适的解决方案吗

提前感谢。

尝试将查询更改为:

$subscribedquery=$this->db->query("select id from usersubscription where plan_id IN 
    ((SELECT DISTINCT plan_id FROM subscribed_videos sv where sv.videoid = $videoid)
    OR id IN (SELECT DISTINCT assosiated_plan_id 
    FROM subscription_groups sg
    JOIN subscribed_videos sv ON sv.plan_id = sg.plan_id
    WHERE sv.videoid = $videoid)) and user_id=$userid");
我添加了括号以更改运算符优先级

尝试将查询更改为:

$subscribedquery=$this->db->query("select id from usersubscription where plan_id IN 
    ((SELECT DISTINCT plan_id FROM subscribed_videos sv where sv.videoid = $videoid)
    OR id IN (SELECT DISTINCT assosiated_plan_id 
    FROM subscription_groups sg
    JOIN subscribed_videos sv ON sv.plan_id = sg.plan_id
    WHERE sv.videoid = $videoid)) and user_id=$userid");

我添加了括号来更改运算符优先级

这就是您要查看的吗

select 
id 
from 
usersubscription 
where 
(
  plan_id 
    IN 
    (
      (
        SELECT DISTINCT plan_id 
        FROM 
        subscribed_videos sv where sv.videoid = 5
      )
    )
   OR id IN 
  (
       SELECT DISTINCT assosiated_plan_id AS plan_id
       FROM subscription_groups sg
       JOIN subscribed_videos sv ON sv.plan_id = sg.plan_id
       WHERE sv.videoid = 5
   )
) 

and user_id=1;

这就是你所看到的吗

select 
id 
from 
usersubscription 
where 
(
  plan_id 
    IN 
    (
      (
        SELECT DISTINCT plan_id 
        FROM 
        subscribed_videos sv where sv.videoid = 5
      )
    )
   OR id IN 
  (
       SELECT DISTINCT assosiated_plan_id AS plan_id
       FROM subscription_groups sg
       JOIN subscribed_videos sv ON sv.plan_id = sg.plan_id
       WHERE sv.videoid = 5
   )
) 

and user_id=1;

我想说,您应该尝试使用联接

SELECT DISTINCT s.id ,
FROM_UNIXTIME(p.`added_on`),
DATE_ADD(FROM_UNIXTIME(s.`subscribed_on`), INTERVAL p.`days_limit` DAY) `expiry_date`
FROM usersubscription s
LEFT JOIN subscribed_videos v ON (s.plan_id = v.plan_id)
LEFT JOIN subscription_groups g ON(s.id = assosiated_plan_id )
LEFT JOIN subscribed_videos sv ON sv.plan_id = g.plan_id
LEFT JOIN `subscription_plans` p ON (p.id = s.plan_id)
WHERE s.user_id=1 AND  sv.videoid = 5
AND  v.videoid = 5
AND  DATE_ADD(FROM_UNIXTIME(s.`subscribed_on`), INTERVAL p.`days_limit` DAY) > CURRENT_DATE()
在上面的查询中,我有一个额外的join
subscription\u plans
来检查您的到期日条件,还请注意,您在查询中直接使用post变量,即
$userid=$\u post['userid']$videoid=$_POST['videoid']
这是不安全的,当您使用codeigniter时,您应该使用活动记录库来构建您的查询,该查询将在其自身端占用所有转义

这是上述查询的活动记录版本

$query = $this->db
    ->select('s.id')
    ->distinct()
    ->from('usersubscription s')
    ->join('subscribed_videos v ','s.plan_id = v.plan_id','LEFT')
    ->join('subscription_groups g ','s.id = assosiated_plan_id','LEFT')
    ->join('subscribed_videos sv','sv.plan_id = g.plan_id','LEFT')
    ->join('`subscription_plans` p','p.id = s.plan_id','LEFT')
    ->where('s.user_id',$userid)
    ->where('sv.videoid',$videoid)
    ->where('v.videoid',$videoid)
    ->where('DATE_ADD(FROM_UNIXTIME(s.`subscribed_on`), INTERVAL p.`days_limit` DAY) > CURRENT_DATE()',null,FALSE)
    ->get();

我想说你应该尝试使用连接

SELECT DISTINCT s.id ,
FROM_UNIXTIME(p.`added_on`),
DATE_ADD(FROM_UNIXTIME(s.`subscribed_on`), INTERVAL p.`days_limit` DAY) `expiry_date`
FROM usersubscription s
LEFT JOIN subscribed_videos v ON (s.plan_id = v.plan_id)
LEFT JOIN subscription_groups g ON(s.id = assosiated_plan_id )
LEFT JOIN subscribed_videos sv ON sv.plan_id = g.plan_id
LEFT JOIN `subscription_plans` p ON (p.id = s.plan_id)
WHERE s.user_id=1 AND  sv.videoid = 5
AND  v.videoid = 5
AND  DATE_ADD(FROM_UNIXTIME(s.`subscribed_on`), INTERVAL p.`days_limit` DAY) > CURRENT_DATE()
在上面的查询中,我有一个额外的join
subscription\u plans
来检查您的到期日条件,还请注意,您在查询中直接使用post变量,即
$userid=$\u post['userid']$videoid=$_POST['videoid']
这是不安全的,当您使用codeigniter时,您应该使用活动记录库来构建您的查询,该查询将在其自身端占用所有转义

这是上述查询的活动记录版本

$query = $this->db
    ->select('s.id')
    ->distinct()
    ->from('usersubscription s')
    ->join('subscribed_videos v ','s.plan_id = v.plan_id','LEFT')
    ->join('subscription_groups g ','s.id = assosiated_plan_id','LEFT')
    ->join('subscribed_videos sv','sv.plan_id = g.plan_id','LEFT')
    ->join('`subscription_plans` p','p.id = s.plan_id','LEFT')
    ->where('s.user_id',$userid)
    ->where('sv.videoid',$videoid)
    ->where('v.videoid',$videoid)
    ->where('DATE_ADD(FROM_UNIXTIME(s.`subscribed_on`), INTERVAL p.`days_limit` DAY) > CURRENT_DATE()',null,FALSE)
    ->get();


@Marcin…Getting error
子查询返回多于1行
@Marcin…Getting error
子查询返回多于1行
如果您将表格和数据以及预期结果添加到您的问题中,这将是一件好事。请检查此fiddle@Jenz是否可以添加您需要从问题返回的所需输出query@Khalid我会更新的我的问题在这里。@Khalid请看我更新的问题。如果您将表格和数据以及预期结果添加到您的问题中,这将是一件好事。请检查此提琴@Jenz您可以添加您需要从您的问题返回的所需输出吗query@Khalid我会在这里更新我的问题。@Khalid请看我更新的问题。@Abhik..非常感谢..是的工作..我怎样才能只找到未过期的计划。我在问题中已经解释过了。你能帮我想一想如何在这个查询中实现它吗?你可以按照@Khalid的建议去做,也就是说,用JOIN代替subquery。@AbhikChakraborty对不起,伙计,我抢到了你接受的答案,但你已经得到了我的投票answer@MKhalidJunaid我总是主张更好的答案,你的答案比我好得多,使用联接使查询在可读性和性能方面优于子查询。更好的答案总是对其他人有帮助:)@Abhik.非常感谢..它起作用了..我怎么才能只找到那些没有过期的计划呢。我在问题中已经解释过了。你能帮我想一想如何在这个查询中实现它吗?你可以按照@Khalid的建议去做,也就是说,用JOIN代替subquery。@AbhikChakraborty对不起,伙计,我抢到了你接受的答案,但你已经得到了我的投票answer@MKhalidJunaid我总是主张更好的答案,你的答案比我好得多,使用联接使查询在可读性和性能方面优于子查询。更好的答案总是有助于他人:)但这是返回记录,即使我在一个月前订阅了。仅当我已订阅所选视频的计划且该计划尚未过期时,查询才应返回记录(如果我订阅的视频的天数限制为15天,则在订阅之日起15天后尝试时,我将无法获得结果)@Jenz如何可能阅读最后一个where子句,它只是检查
添加的+天数限制
是否大于今天的日期,然后返回,这意味着它尚未过期,现在可以显示您正在尝试的示例数据吗?我添加了
1380652200
(对应于2013年10月1日的日期)与计划id 1对应的
usersubscription
表中的
subscribed\u相同,计划id 1的天数限制为15天。但它仍在返回记录。@Jenz查看我更新的查询我在检查到期日期时出错了,我本应使用
subscribed\u on
而不是
added\u on
查看它是否工作,但这是返回记录,即使我在一个月前订阅了。仅当我已订阅所选视频的计划且该计划尚未过期时,查询才应返回记录(如果我订阅的视频的天数限制为15天,则在订阅之日起15天后尝试时,我将无法获得结果)@Jenz如何可能阅读最后一个where子句,它只是检查
添加的+天数限制
是否大于今天的日期,然后返回,这意味着它尚未过期,现在可以显示您正在尝试的示例数据吗?我添加了
1380652200
(对应于2013年10月1日的日期)作为计划id对应的
usersubscription
表中的
subscription\u