【问题标题】:SQL queries, comparing data between tables, strings and intsSQL 查询,比较表、字符串和整数之间的数据
【发布时间】:2012-06-06 18:15:56
【问题描述】:

这更像是一个“方法”问题,我还没有拿到代码。但我是 SQL 和 php 的新手,想聪明地解决这个问题。

场景如下:

我有一个名为 Donations 的表,每个表在名为 AREA 的列中都有一个字符串值。 AREA 可以具有九个预定值中的任何一个(东北、西北、市中心等)。

我还有一张志愿者表,每个志愿者都指定了他们愿意前往的地区,以帮助领取捐款。对于每个志愿者,我有 9 列,每列有 1 或 0,对应上面列出的九个区域(NW、NE、DT 等...)

我想运行一个查询、一系列查询或 php/sql 组合,我可以在其中搜索所有活跃的捐赠,获得它们所在的区域,然后查询志愿者表,并返回电子邮件地址列表仅适用于愿意前往其中一个或多个地区的志愿者。

感谢任何帮助。 (顺便说一句,这两个表之间没有共享键值。)

【问题讨论】:

    标签: php mysql sql database join


    【解决方案1】:

    我会考虑将区域设为自己的表(ID、名称)。然后为 Donations 表添加 AreaID (ForeignKey) 而不是 Area 字符串列。

    对于志愿者 - 区域协会,我会考虑制作一个名为 VolunteerAreas 的链接表,其结构为 VolunteerID,AreaID。

    编写一些脚本来获取现有数据并将其转储为新格式应该很简单。

    那你可以做...

    获得积极捐款

    SELECT * FROM Donations WHERE Active = 1
    

    从选定区域获取电子邮件

    SELECT Email FROM Volunteers v
    JOIN VolunteerAreas va ON va.VolunteerID = v.ID
    WHERE va.AreaID = @AreaID
    

    【讨论】:

      【解决方案2】:

      你的第一个查询看起来像

      SELECT [area] FROM [database] WHERE donationSelector = selectedValue
      

      然后根据你从上面得到的$area变量将变量$i设置为列名

      <?php
      switch($area) {
          case "Northwest" :
              $i = "NW";
              break;
          case "Northeast" :
              $i = "NE";
              break;
          ...etc.
      }
      

      然后进行另一个查询

      SELECT * FROM [database] WHERE %s = 1, $i
      

      【讨论】:

      • 嘿汉斯,上面的 lokos 不错,但它不是只适用于一次捐赠吗?我需要它才能一次返回多个捐款。
      • 在这种情况下,只需将该代码放入 while($row = mysql_fetch_array($result)) 块中,然后放入 $area = $row['AREA'];。然后 $i 现在是您正在构建的字符串,带有 $i .= ((strlen($i) &gt; 0) ? "WHERE NE = 1" : " AND NE = 1");
      【解决方案3】:

      我强烈建议您更改架构,使用多个表而不是两个。

      下面的 SQL 是一个没有主键、外键、索引等的骨架。

      CREATE TABLE area (
        id           INT NOT NULL AUTOINCREMENT,
        name         VARCHAR(128)
      )
      
      CREATE TABLE volunteer (
        id           INT NOT NULL AUTOINCREMENT,
        name         VARCHAR(128)
      )
      
      CREATE TABLE coverage (
        area_id      INT,
        volunteer_id INT
      )
      

      首先,在前两个表中使用代理主键(id 列)意味着您可以更改实体的名称而不会破坏任何内容。

      其次,当你添加新区域时,你只需要在每个表中添加新记录,而不是在志愿者表中添加新的二进制标志字段。

      第三,查询变得更整洁、更易维护、更快……

      SELECT
        volunteer.*
      FROM
        area
      INNER JOIN
        coverage
          ON area.id = coverage.area_id
      INNER JOIN
        volunteer
          ON volunteer.id = coverage.volunteer_id
      WHERE
        area.name IN ('NW', 'SE')
      GROUP BY
        volunteer.id
      

      【讨论】:

        【解决方案4】:

        所以,我完全通过一种完全不同的方法解决了这个问题,尽管我确信上述方法会奏效。

        我为每个区域分配了一个质数,从 2、3、5 等开始...然后当志愿者注册时,它通过乘以他们愿意去的区域为他们创建一个代码。

        我对捐赠使用了相同的质数,并为每笔捐赠分配了适当的质数。

        然后我运行了这个连接查询,看看志愿者的代码是否可以被任何可用的捐款整除。

        $q = "Select Distinct(EMAIL) from PUPS where EXISTS (Select * from Donations where STATUS = 'ACTIVE' AND (REGIONCODE Mod AREAPRIME = 0))";

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2012-11-27
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多