【问题标题】:Converting Relational Algebra to corresponding SQL Query将关系代数转换为相应的 SQL 查询
【发布时间】:2016-04-17 15:29:53
【问题描述】:

我正在尝试了解如何正确地将 关系代数 转换为 SQL 查询

我发现这是我难以转换的事情之一。有人可以分享任何提示吗?

表格:

Room(_roomId_, numberOfBeds, price)

Guest(_guestId_, homeTown, age)

Reservation(_roomId_, _guestId_, date)

关系代数:

Πprice(ΠroomId(ΠguestId(σage<20)Guest) Natural Join Reservation) Natural Join Room

查询: 我设法从部分陈述中推断出以下内容:

SELECT roomId FROM (SELECT guestID from Guest WHERE age<20) Natural Join Reservation

我接近了吗?

【问题讨论】:

    标签: mysql sql relational-algebra


    【解决方案1】:

    您可以通过多种方式来看待这个问题。如果您比关系代数更熟悉数据库,则第一个选项可能更容易,而如果您熟悉关系代数,则第二个选项会更容易(并且对于更复杂的问题更准确)。

    表格优先:

    首先弄清楚你的连接。你知道你有你的三组(表)GuestReservationRoom,所有三个 with 都是自然连接的(内连接)。所以你可以像这样开始写你的查询:

    SELECT *
    FROM Guest g
        INNER JOIN Reservation res
            ON g._guestId_ = res._guestId_
        INNER JOIN Room r
            ON res._roomId_ = r._roomId_;
    

    完成后,应用您的条件:

    SELECT *
    FROM Guest g
        INNER JOIN Reservation res
            ON g._guestId_ = res._guestId_
        INNER JOIN Room r
            ON res._roomId_ = r._roomId_
    WHERE g.age < 20;
    

    或者,您可以将g.age 的条件放在Reservation 的连接中,但建议将条件放在INNER JOINWHERE 子句中。

    最后,您填写您的SELECT

    SELECT g._guestId_,
        res._roomId_,
        r.price
    FROM Guest g
        INNER JOIN Reservation res
            ON g._guestId_ = res._guestId_
        INNER JOIN Room r
            ON res._roomId_ = r._roomId_
    WHERE g.age < 20;
    

    操作顺序

    为此,您可以使用操作顺序编写查询。所以括号内的所有内容都会首先执行。这样做,您首先编写针对Guest 的查询:

    SELECT g._guestId_
    FROM Guest g
    WHERE g.age < 20;
    

    下一组是Reservations,这是自然加入的:

    SELECT g._guestId_,
        res._roomId_
    FROM Guest g
        INNER JOIN Reservation res
            ON g._guestId_ = res._guestId_;
    

    终于来到Room集合,再次自然加入:

    SELECT g._guestId_,
        res._roomId_,
        r.price
    FROM Guest g
        INNER JOIN Reservation res
            ON g._guestId_ = res._guestId_
        INNER JOIN Room r
            ON res._roomId_ = r._roomId_
    WHERE g.age < 20;
    

    【讨论】:

      【解决方案2】:

      应该是这样的..

      SELECT price, _roomId_ FROM room 
      inner join Reservation on (reservation._roomId_ = room._roomId_
      inner join Guest  on (reservation._guestId = guest._guestId and age <20) ;
      

      在您的关系代数符号中,您有priceroomId 的项目(选择)然后您在Guest and Reservation 和这个笛卡尔积and Room 之间的自然连接.. 自然连接在sql 通过关系两侧主键的内部连接.. 最后你在guest age 上有一个条件,这通常是由 where 子句管理的条件或直接在连接条件中添加一个 and 子句

      【讨论】:

      • 自然连接类似于公共列的成对相等的内部连接,每对中的一列被删除。它与 PK 无关,并且您没有提到在文本中删除列(但您在代码中这样做了)。 @RandomMath 这最终对你有帮助吗?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-04-01
      • 1970-01-01
      • 2013-04-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多