Neo4j - 24/7赌场名单

时间:2014-01-18 11:55:24

标签: neo4j data-modeling graph-databases rostering

这是一系列新问题,以回应肯尼对我之前关于如何围绕24/7赌场名单建立数据库模型的问题的回答。 Database model for a 24/7 Staff roster at a casino

仍然试图了解图表以及如何遍历/连接数据。使用Kenny的答案中图像上半部分的时间图表,每年有12个月的节点,然后指向一行日节点,其中第一天有超过一天的节点,值为1月?我会为每年构建这些子图,还是会使用一个特定的查询来添加一个随时间推移而不存在的节点?我知道有一个查询可以做到这一点,但它需要考虑月节点中的最后一天并创建正确的结束关系?我是否会遇到闰年或夏令时的任何问题?

在答案图片的下半部分是游戏节点,他们只有一个员工和位置关系吗?我不知道如何判断哪个员工被分配到哪个表(没有向关系边添加属性),我应该向边添加属性还是应该为每对使用单独的节点?

我制作了一张粗略的图像,以显示笔/纸名单的外观,它可能在某种程度上有所帮助。 Roster example

我还试图计划一个带有一些问题的图表(红色框),它是在插画中完成的并且有点乱,我很想知道Kenny的图形图像是否在特定的应用程序中完成,如果所以哪一个,虽然我在视觉上看它的图形往往会纠结和混乱。

Graph model concept
您似乎无法单击图像以查找文本可读的直接链接,您可以在此处查看:http://i.imgur.com/FMfJx6G.png

如果有帮助我可以在此处添加问题文本或使用建议的软件重新创建图表。

1 个答案:

答案 0 :(得分:7)

以下是24/7 Staff roster at a casino的数据库模型的原始图像:

24/7 Staff Roster at a Casino

  

在Kenny的答案中,时间图表位于图像的上半部分,   每年有12个月的节点,然后指向一行   节点,其中有超过一天的节点,值为1   一个月的第一天?

是的,这是正确的。我在下面的图片中对此进行了建模。

Multilevel Datetime Index

  

我会为每年制作这些子图,还是会使用特定的子图   查询添加一个随时间推移不存在的节点?一世   了解有一个查询可以做到这一点,但它需要   记帐月份节点中的最后一天并创建结束   关系正确吗?

我创建了一个Cypher脚本,用于创建年,月,日,小时的多级时间索引。你可以在这里找到:

https://gist.github.com/kbastani/8519557

例如,要创建一天中的所有小时,我们可以合并任何一天,然后再添加年份结构。这是MERGE Cypher声明的优势之一。用于创建多级日期时间索引的Cypher查询以“容错”的方式,如果您多次运行它,那么它将不会创建重复项或弄乱您的数据结构。

以下是用于合并日期和小时的2级层次结构的Cypher脚本:

// Enter the day you would like to create
WITH { day: 18, month: 1, year: 2014 } as dayMap

// Merge hours in a day
MERGE (thisDay:Day 
       { 
           day: dayMap.day, 
           month: dayMap.month, 
           year: dayMap.year 
       })

// Get the first hour in the day (hour 1)
MERGE (firstHour:Hour 
       { 
           day: dayMap.day, 
           month: dayMap.month, 
           year: dayMap.year, 
           hour: 1 
       })

// Connect this day to first hour
CREATE (thisDay)-[:FIRST]->(firstHour)

// For each i in (2-24)
FOREACH (i IN tail(range(1, 24)) |

    // Get this hour
    MERGE (thishour:Hour 
           { 
              day: dayMap.day, 
              month: dayMap.month, 
              year: dayMap.year, 
              hour: i 
           })

    // Get the hour before this hour
    MERGE (lasthour:Hour 
           { 
              day: dayMap.day, 
              month: dayMap.month, 
              year: dayMap.year, 
              hour: i - 1 
           })

    // Link the hours
    CREATE (lasthour)-[:NEXT]->(thishour))

// Get the last hour in the sequence (hour 24)
MERGE (lastHour:Hour 
      { 
           day: dayMap.day, 
           month: dayMap.month, 
           year: dayMap.year, 
           hour: 24 
      })

// Connect this day to the last hour
CREATE (thisDay)-[:LAST]->(lastHour)
  

闰年会有任何问题吗?   或夏令时?

不,这应该不是问题,但可能取决于您提出的问题。这是特定于上下文的。由于我们不依赖于数据结构来在用户界面中构建日历,而是只回答有关特定日期的特定问题,因此规则将从导入的数据继承。

  

在答案图片的下半部分是游戏节点,只做它们   有一个员工和位置关系?我不确定我怎么做   告诉哪个员工被分配到哪个表(不添加   属性到关系边缘),我应该添加属性   到边缘或我应该为每对使用单独的节点?

有一个员工节点和一个位置节点。这样,您可以从员工节点或位置节点开始,以了解有关该对象的某些事项以及它与其他对象的关系。

  

我还试图计划出一些带有问题的图表(红框),它   在插画中完成并且有点凌乱,我很想知道是否   Kenny的图形图像是在特定应用程序中完成的,如果是的话   哪一个,虽然我把它视觉图形倾向于纠结和   凌乱。

我用来生成图形数据模型图像的工具是http://www.apcjones.com/arrows/#

要连接节点,只需在节点的圆圈外部突出显示鼠标指针,然后单击并将关系拖动到另一个节点。这个小应用程序是开源的,只适用于Chrome浏览器。

至于你的完整数据模型,我构建了一个Cypher数据集示例,因为我真的认为你的域很有趣。您可以在此处找到这些查询:https://gist.github.com/kbastani/8529380

以下是我使用的数据模型:

24/7 Staff Roster at a Casino expanded

回到上一篇文章,您有了一个问题:

  

在特定日期,有多名员工在场上工作了80分钟或更长时间?

以下是回答该问题的Cypher查询:

// What staff have been on the floor for 80 minutes or more on a specific day?
WITH { day: 18, month: 1, year: 2014 } as dayMap

// The dayMap field acts as a parameter for this script
MATCH (day:Day { day: dayMap.day, month: dayMap.month, year: dayMap.year }),
      (day)-[:FIRST|NEXT*]->(hours:Hour),
      (hours)<-[:BEGINS]-(game:Game),
      (game)<-[:DEALS]-(employee:Employee)

WITH game, employee

ORDER BY game.timestamp DESC
WITH employee, head(collect(game)) as game

MATCH (game)<-[:CONTINUE*]-(games)

WITH employee.firstname as first_name, 
     employee.lastname as last_name, 
     SUM(games.interval) as time_on_floor

// Only return results for staff on the floor more than 80 minutes
WHERE time_on_floor > 80
RETURN first_name, last_name, time_on_floor