sqlite 如何用3个表建模多对多数据库

bd1hkmkf  于 2022-12-19  发布在  SQLite
关注(0)|答案(2)|浏览(137)

我正在做一个django的后端,我正在尝试建立一个数据库模型,并希望以最佳实践的方式来做。我需要一个“用户”表,一个“投资组合”表和一个“股票”表。一个用户可以有多个投资组合,其中包括多个股票。
这是我的代码:

class User(models.Model):
    user_id = models.AutoField(primary_key=True)
    username = models.CharField(max_length=25)
    in_cash = models.DecimalField(max_digits=15, decimal_places=2)

class Portfolios(models.Model):
    portfolio_id = models.AutoField(primary_key=True)
    user_id = models.ForeignKey("User", on_delete=models.CASCADE)
    stock_id = models.ForeignKey("Stocks", on_delete=models.CASCADE)
    buy_datetime = models.DateTimeField(default=datetime.now, blank=True)
    number_of_shares = models.IntegerField()

class Stocks(models.Model):
    stock_id = models.AutoField(primary_key=True)
    stock_symbol = models.CharField(max_length=12)

在我的脑海里,我会在“投资组合”表中为投资组合中的每只股票都写上一个条目,所以“投资组合”看起来像这样

  • 门户类1,用户ID:1、长袜:1、购买日期:2019年1月12日,股份:20
  • 门户类1,用户ID:1、长袜:2、购买日期:2020年2月19日,股份:41

所以有一个投资组合,包含两支股票,但总体上看不太对,如果像我上面的例子那样使用,我不能把portfolioid作为主键,我该如何改进呢?
谢谢你抽出时间

kqqjbcuj

kqqjbcuj1#

让我困惑的是名称portfolio,我将其命名为position。您最初的代码是正确的,尽管我做了一些修改,删除了可能不需要的AutoField,使用OneToOneFieldCustomer连接到User,删除了类名末尾的s,类名是模板,因此应该是单数,而不是复数。将priceStock相加,最后改变PortfolioPortfolio应为所有Position

from django.conf import settings

class Customer(models.Model):
    customer = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.CASCADE,)
    in_cash = models.DecimalField(max_digits=15, decimal_places=2)

    def __str__(self):
        return self.customer.username

class Position(models.Model):
    customer = models.ForeignKey(Customer, on_delete=models.CASCADE)
    stock = models.ForeignKey('Stock', on_delete=models.CASCADE)
    number_of_shares = models.IntegerField()
    buy_datetime = models.DateTimeField(default=datetime.now, blank=True)

    def __str__(self):
        return self.customer.customer.username + ": " + str(self.number_of_shares) + " shares of " + self.stock.stock_symbol
    
class Stock(models.Model):
    stock_symbol = models.CharField(max_length=12)
    price = models.DecimalField(max_digits=10, decimal_places=2)

    def __str__(self):
        return self.stock_symbol

在我的脑海里,我会在“投资组合”表中为投资组合中的每只股票都写上一个条目,所以“投资组合”看起来像这样

portfolioid 1, userid: 1, stockid: 1, buydate: 12.01.2019, shares: 20
portfolioid 1, userid: 1, stockid: 2, buydate: 19.02.2020, shares: 41

所以有一个投资组合,包含两支股票,但总体上看不太对,如果像我上面的例子那样使用,我不能把portfolioid作为主键,我该如何改进呢?
您是正确的,只是应该应用于位置,每个位置都是唯一的,而不是PortfolioPortfolioCustomer具有的Position全部

ou6hu8tu

ou6hu8tu2#

与通常的多对多情况一样,您需要创建一个intermediary table,也称为junction table/association tableAssociative Entity
您的用户将拥有多个投资组合:

class UserPortfolio(models.Model):
    user_id = models.ForeignKey("User")
    portfolio_id = models.ForeignKey("Portfolio")

投资组合中包含多只股票:

class PortfolioStock(models.Model):
    portfolio_id = models.ForeignKey("Portfolio")
    stock_id = models.ForeignKey("Stock")

现在一个用户可以有几个投资组合,这些投资组合将包括几只股票。为了访问用户对应的股票,您将需要连接表。

相关问题