代表 NCAA 篮球赛的最佳模式

发布于 2024-07-15 07:34:58 字数 536 浏览 5 评论 0原文

代表 NCAA 男子篮球分组的最佳数据库模式是什么? 如果您不熟悉,请点击以下链接:http://www.cbssports.com/ Collegebasketball/mayhem/brackets/viewable_men

我可以看到几种不同的方法可以对这些数据进行建模,使用单个表、多个表、硬编码列、有些动态的方法等。您需要一种方法来建模每支球队的种子队和名次,以及每场比赛和每场比赛的结果(可能还有得分)。 您还需要一种方法来表示谁在锦标赛的哪个阶段与谁比赛。

本着疯狂三月的精神,我认为这是一个很好的问题。 这里有一些明显的答案,这个问题的主要目标是看看你可以回答它的所有不同方式。 哪种方式最好可能取决于您所使用的语言或您使用它的具体方式,但请尽量保持答案与数据库、语言无关并且保持相当高的水平。 如果有人对更好的方式来表达这个问题或更好的方式来定义它有任何建议,请在评论中告诉我。

What is the best database schema to represent an NCAA mens basketball bracket? Here is a link if you aren't familiar: http://www.cbssports.com/collegebasketball/mayhem/brackets/viewable_men

I can see several different ways you could model this data, with a single table, many tables, hard-coded columns, somewhat dynamic ways, etc. You need a way to model both what seed and place each team is in, along with each game and the outcome (and possibly score) of each. You also need a way to represent who plays who at what stage in the tournament.

In the spirit of March Madness, I thought this would be a good question. There are some obvious answers here, and the main goal of this question is to see all of the different ways you could answer it. Which way is best could be subjective to the language you are using or how exactly you are working with it, but try to keep the answers db agnostic, language agnostic and fairly high level. If anyone has any suggestions on a better way to word this question or a better way to define it let me know in the comments.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(8

简单气质女生网名 2024-07-22 07:34:58

人们自然倾向于按照比赛进行的顺序查看括号。 您从外到内阅读传统的图表。但让我们反过来想一下。 每场比赛都在两队之间进行。 一个赢了,另一个输了。

现在,还有更多的事情要做。 特定两场比赛的获胜者将在另一场比赛中对阵。 因此,游戏本身之间也存在着某种关系,无论谁在玩这些游戏。 也就是说,每场比赛(第一轮除外)中对阵的球队是前两场比赛的获胜者。

因此,您可能会注意到,每场比赛之前都有两个“子比赛”,并决定谁在该比赛中对阵。 这听起来就像一棵二叉树:每个根节点最多有两个子节点。 如果您知道每场比赛谁获胜,您可以轻松确定“父”比赛中的球队。

因此,要设计一个数据库来对此进行建模,您实际上只需要两个实体:TeamGame。 每个Game都有两个与其他Game相关的外键。 名称并不重要,但我们会将它们建模为单独的键,以强制执行每个游戏不超过两个先前游戏的要求。 我们将它们称为 leftGamerightGame,以与二叉树命名法保持一致。 同样,我们应该有一个名为 parentGame 的键来跟踪反向关系。

此外,正如我之前提到的,您可以通过查看前两场比赛的获胜者来轻松确定每场比赛中对阵的球队。 所以你实际上只需要跟踪每场比赛的获胜者。 因此,为 Game 实体提供一个指向 Team 表的 winner 外键。

现在,有一个小问题,就是播种支架。 也就是说,对第一轮比赛的比赛进行建模。 您可以通过为整个比赛中的每个团队设置一个游戏来对此进行建模,其中该团队是获胜者并且之前没有任何游戏。

因此,整体架构将是:

Game:
    winner: Team
    leftGame: Game
    rightGame: Game
    parentGame: Game
    other attributes as you see fit

Team:
    name
    other attributes as you see fit

当然,您可以将所需的所有其他信息添加到实体中:位置、分数、结果(如果游戏因放弃或其他异常情况而获胜)。

The natural inclination is to look at a bracket in the order the games are played. You read the traditional diagram from the outside in. But let's think of it the other way around. Each game is played between two teams. One wins, the other loses.

Now, there's a bit more to it than just this. The winners of a particular pair of games face off against each other in another game. So there's also a relationship between the games themselves, irrespective of who's playing in those games. That is, the teams that face off in each game (except in the first round) are the winners of two earlier games.

So you might notice that each game has two "child games" that precede it and determine who faces off in that game. This sounds exactly like a binary tree: each root node has at most two child nodes. If you know who wins each game, you can easily determine the teams in the "parent" games.

So, to design a database to model this, you really only need two entities: Team and Game. Each Game has two foreign keys that relate to other Games. The names don't matter, but we would model them as separate keys to enforce the requirement that each game have no more than two preceding games. Let's call them leftGame and rightGame, to keep with the binary tree nomenclature. Similarly, we should have a key called parentGame that tracks the reverse relationship.

Also, as I noted earlier, you can easily determine the teams that face off in each game by looking at who won the two preceding games. So you really only need to track the winner of each game. So, give the Game entity a winner foreign key to the Team table.

Now, there's the small matter of seeding the bracket. That is, modeling the match-ups for the first round games. You could model this by having a Game for each team in the overall competition where that team is the winner and has no preceding games.

So, the overall schema would be:

Game:
    winner: Team
    leftGame: Game
    rightGame: Game
    parentGame: Game
    other attributes as you see fit

Team:
    name
    other attributes as you see fit

Of course, you would add all the other information you'd want to the entities: location, scores, outcome (in case the game was won by forfeit or some other out of the ordinary condition).

梦幻之岛 2024-07-22 07:34:58

对于 RDBMS,我认为仍然足够灵活以适应大多数情况的最简单方法是执行以下操作:

  • Teams[team-id (PK)]、[名称][区域 ID(FK 到区域)][初始种子] >。 每个团队都会有一份参赛作品。 (地区表是一个简单的代码表,只有四个条目,每个 NCAA 地区一个,此处未列出。)

  • 参与者 具有[游戏 ID(FK 到 < strong>游戏)][团队 ID(FK 到团队)][得分(可为空)],[结果][score] 可以为空,以反映团队可能会失败。 每个游戏通常有两名参与者。

  • 游戏具有[游戏 ID (PK)][日期][位置]。 要了解哪些球队参加了比赛,请在“参与者”表中查找相应的比赛 ID。 (请记住,如果有人退出或被取消资格,可能会有两个以上的团队。)

要设置初始分组,请将适当的种子相互匹配。 比赛进行时,请注意哪支球队在特定比赛中结果 = 获胜者; 该队将与另一场比赛的获胜者进行比赛。 填写括号,直到不再有获胜球队为止。

For a RDBMS, I think the simplest approach that's still flexible enough to accommodate the majority of situations is to do the following:

  • Teams has [team-id (PK)], [name], [region-id (FK to Regions)], [initial-seed]. You will have one entry for each team. (The regions table is a trivial code table with only four entries, one for each NCAA region, and is not listed here.)

  • Participants has [game-id (FK to Games)], [team-id (FK to Teams)], [score (nullable)], [outcome]. [score] is nullable to reflect that a team might forfeit. You will have typically have two Participants per Game.

  • Games has [game-id (PK)], [date], [location]. To find out which teams played in a game, look up the appropriate game-id in the Participants table. (Remember, there might be more than two teams if someone dropped out or was disqualified.)

To set up the initial bracket, match the appropriate seeds to each other. As games are played, note which team has outcome = Winner for a particular game; this team is matched up against the winner of another game. Fill in the bracket until there are no more winning teams left.

谜兔 2024-07-22 07:34:58

由于您没有指定 RDBMS,因此我将采取一些不同的做法并采用 CouchDB 方法,因为我本周末正在阅读该方法。 这是我提出的代表游戏的文档结构。

{
  "round" : 1, //The final would be round 5, and I guess Alabama St. vs. Morehead would be 0
  "location" : "Dayton, OH",
  "division": "South",
  "teams" : ["UNC", "Radford"]  //A feature of Couch is that fields like teams don't need a fixed nuber of columns.
  "winner" : "UNC"  //Showing my bias
}

更有趣或更完整的应用程序可能还会在某处存储团队、排名等数据。 约翰的方法似乎很好地涵盖了这个角度。 我欢迎更了解我的沙发技能的人提出任何评论。

Since you didn't specify RDBMS, I'm gonna be a little different and go with a CouchDB approach since I was reading about that this weekend. Here's the document structure I've come up with a represent a game.

{
  "round" : 1, //The final would be round 5, and I guess Alabama St. vs. Morehead would be 0
  "location" : "Dayton, OH",
  "division": "South",
  "teams" : ["UNC", "Radford"]  //A feature of Couch is that fields like teams don't need a fixed nuber of columns.
  "winner" : "UNC"  //Showing my bias
}

A more interesting or complete application might have data for teams, rankings, and the like stored somewhere as well. John's approach covers that angle well, it seems. I welcome any comments from people who know better on my Couch skills.

温柔一刀 2024-07-22 07:34:58

我创建了一个包含以下表格的小型系统:

游戏:GameId、TournId、RoundId、Sequence、Date、VisitorId、VisitorScore、HomeId、HomeScore、WinnerId、WinnerGameId、WinnerHome(位)

预测:PredId、UserId、GameId、PredVisitorId、PredHomeId、 PredWinnerId

回合:RoundId、TournId、RoundNum、Heading1、Heading2

团队:TeamId、TournId、TeamName、Seed、MoreInfo、Url

锦标赛:TournId、TournDesc

用户:TournId、用户名

WinnerGameId 将一场比赛的获胜者与他们的下一场比赛连接起来。 WinnerHome 告诉获胜者是下一场比赛的主场还是客队。 除此之外,我认为这是不言自明的。

I created a small system with the following tables:

Games: GameId, TournId, RoundId, Sequence, Date, VisitorId, VisitorScore, HomeId, HomeScore, WinnerId, WinnerGameId, WinnerHome (bit)

Predictions: PredId, UserId, GameId, PredVisitorId, PredHomeId, PredWinnerId

Rounds: RoundId, TournId, RoundNum, Heading1, Heading2

Teams: TeamId, TournId, TeamName, Seed, MoreInfo, Url

Tournaments: TournId, TournDesc

Users: TournId, UserName

WinnerGameId connects the winner of a game to their next game. WinnerHome tells whether the winner is the home or visitor of that next game. Other than that, I think it's pretty self explanatory.

醉态萌生 2024-07-22 07:34:58

提议的模型

提议的 ER 图 http://img257.imageshack.us/img257/1464/ncaaer .jpg

团队表

我们只需要了解团队的名称和种子即可。 因此我们需要一个“Team”表来存储种子值。 唯一的候选键是团队名称,因此我们将使用它作为主要键以保持简单。 NCAA 球队名称不太可能在一场锦标赛中发生变化或包含重复名称,因此它应该是一个足够的密钥。

比赛表

“比赛”表可用于将球队配对到每场比赛中。 “团队”的外键(FK1、FK2)将确保团队存在,并且这些值的主键确保团队仅相互匹配一次。

“MatchUp”表中“Team”表的外键 (FK4) 将记录获胜者。 从逻辑上讲,获胜者必须是参加比赛的两支球队之一。 针对主键的检查约束可以确保这一点。

一旦比赛结果确定,就可以从球队表中检索胜利者的种子,以便与其他胜利者的种子进行比较,从而确定后续的比赛。 这样做后,可以将所产生的比赛的 FK (FK3) 写入确定比赛,以描述锦标赛的进度(尽管可以随时导出该数据)。

游戏表

我还对每个比赛的游戏进行了建模。 一场比赛是通过它所属的比赛以及基于比赛期间发生的顺序的序列号来识别的。 比赛从团队表(FK2)中选出胜者。 分数也可以记录在此表中。

Proposed Model

Proposed ER Diagram http://img257.imageshack.us/img257/1464/ncaaer.jpg

Team Table

All we need to know about a team is the name and seed. Therefore we need a "Team" table to store the seed value. The only candidate key is team name so we will use that as the primary to keep things simple. NCAA team names are unlikely to change over the course of a single tournament or contain duplicates so it should be an adequate key.

MatchUp Table

A "MatchUp" table can be used to pair the teams into each of the match ups. Foreign Keys (FK1, FK2) to the "Team" will ensure that the teams exist and a primary key over these values ensures that teams are only matched up against each other once.

A foreign key (FK4) to the "Team" table from the "MatchUp" table will record the winner. Logically the winner would need to be one of the two teams participating in the match up. A check constraint against the primary key could ensure this.

Once the outcome of a match up has been determined the Victor's seed could be retrieved from the team table in order to compare against other Victor's in order to determine subsequent match ups. Upon doing so an FK (FK3) to the resulting match up can be written to the determining match ups in order to depict the progress of the tournament (although this data could probably be derived at any time).

Games Table

I also modeled out the games of each Match Up. A game is identified by the match up it is a part of and a sequence number based on the order in which it took place during the match up. Games have a winner from the team table (FK2). Score could be recorded in this table as well.

╰◇生如夏花灿烂 2024-07-22 07:34:58

4 个表:

团队(团队、地区、种子)

用户(用户 ID、电子邮件、blablabla)

支架(BracketId , UserId, Points)

Pick(BracketId, GameId, Team, Points)

一个人提交的每个分组将在 Pick 表中包含 63 行。
每场比赛结束后,您将更新选秀表以对各个选秀进行评分。 对于尚未玩的游戏,此表中的分数字段将为空;对于错误的选择,该表中的分数字段将为 0;对于正确的选择,该表中的分数字段将为正数。 GameId 只是一个关键,用于识别用户选择该选择的位置(例如:East_Round2_Game2、FinalFour_Game1)。

每次更新选择表后,可以更新括号表中的分数列,因此它包含该括号的分数总和。 最受关注的是排行榜,不想每次有人想查看排行榜时都重新汇总这些内容。

您不需要保留包含所有实际进行的比赛或其结果的表格,只需在每场比赛后更新选择表即可。 您甚至可以通过查看选择表中的“点数”列来突出显示正确/不正确的选择。

4 tables:

Team(Team, Region, Seed)

User(UserId, Email, blablabla)

Bracket(BracketId, UserId, Points)

Pick(BracketId, GameId, Team, Points)

Each bracket a person submits will have 63 rows in the Pick table.
After each game is played you would update the pick table to score individual picks. Points field in this table will be null for game not yet played, 0 for an incorrect pick or positive number for correct pick. GameId is just a key identifying where in that users bracket this pick goes (ex: East_Round2_Game2, FinalFour_Game1).

The points column in the bracket table can be updated after each update of the pick table so it contains the sum of points for that bracket. The most looked at thing will be the standings, don't want to re-sum those every time someone wants to view the leader board.

You don't need to keep a table with all the games that actually get played or their results, just update the pick table after each game. You can even do the bracket highlighting of correct/incorrect picks by just looking at the Points column in the pick table.

简美 2024-07-22 07:34:58

跟踪大量不同的括号预测:您可以使用 67 位来跟踪每场比赛的结果。 (即,锦标赛中进行的 67 场比赛均由一位代表,1 =“A 队获胜”,0 =“B 队获胜”)。 要显示任何给定的括号,您可以使用一个非常简单的函数将 67 位映射到 UI。 该函数知道团队名称及其初始位置,然后在跟踪“位板”时通过支架跟踪他们的移动。

In keeping track of a large number of different bracket predictions: You could use 67 bits for keeping track of the outcome of each game. (ie. Each of the sixty-seven games played in the tournament is each represented by a bit, 1 = "team A wins", 0 = "team B wins"). To display any given bracket, you can use a pretty simple function to map the 67 bits to the UI. The function knows the team names and their initial location, and then it tracks their movement through the bracket as it traces the 'bitboard'.

德意的啸 2024-07-22 07:34:58

我对所有数据库使用相同的架构。

t
--------
1 guid PK
2 guid FK
3 bit

然后在我的代码中:

select [2],[3] from t where [1] = @1

@1是我正在获取的数据的id。 然后,如果 [2] 不为空,我再次选择,将 @1 设置为 [2]。

这使得对您发布的情况进行建模变得非常容易。

I use the same schema for all of my databases.

t
--------
1 guid PK
2 guid FK
3 bit

Then in my code:

select [2],[3] from t where [1] = @1

@1 is the id of the data I am fetching. Then if [2] is not null, I select again, setting @1 to [2].

This makes it really easy to model the situation you posted.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文