草庐IT

MongoDB 存储和查询价格历史

coder 2023-11-03 原文

我正在处理一组数据,这是一个产品目录。只有大约 20,000 种商品,并且很少发生价格变化。最多每月可能更新 100 次。

但是,在这种情况下,价格变化很有趣,我想长期跟踪价格。

我正在尝试找到以易于查询的方式存储价格数据的最佳方式。

目前它存储在产品文档中的一个数组中。只需价格和时间戳。给定少量且相当静态的数据集,您将如何设计模型?

另外,还有一个额外的问题,过滤器应该是什么样子才能给出当前价格低于前一个的产品列表?

示例数据,模型的简化版本:

// Match, current price is lower than previous price

db.TestC.insert({Name: "P1", CurrentPrice: 10.0,  PriceHistory: [{Price: 14.0, Timestamp: ISODate("2019-04-26T07:11:11.939Z")}, {Price: 12.0, Timestamp: ISODate("2019-04-27T07:11:11.939Z")}]})

// No match, price history doesn't exist yet

db.TestC.insert({Name: "P2", CurrentPrice: 10.0, PriceHistory: null})

// No match, previous price was lower than current price

db.TestC.insert({Name: "P3", CurrentPrice: 18.0, PriceHistory: [{Price: 14.0, Timestamp: ISODate("2019-04-26T07:11:11.939Z")}, {Price: 12.0, Timestamp: ISODate("2019-04-27T07:11:11.939Z")}]})

在对此进行更多工作后进行编辑:

所以,我终于想出了我需要的东西,并认为我应该分享以防它对某人有帮助:

db.TestCollection.aggregate({
    '$project': {
      'Number': 1, 
      'AssortmentKey': 1, 
      'AssortmentName': 1, 
      'NameExtension': 1, 
      'Name': 1, 
      'CurrentPrice': {
        '$arrayElemAt': [
          '$PriceHistory', -1
        ]
      }, 
      'PreviousPrice': {
        '$arrayElemAt': [
          '$PriceHistory', -2
        ]
      }
    }
  }, {
    '$match': {
      '$expr': {
        '$lt': [
          '$CurrentPrice.Price', '$PreviousPrice.Price'
        ]
      }
    }
  })

最佳答案

实际上,我会以相同的方式组织文档。请记住,MongoDB 有每个文档 16 MB 的硬限制,这是非常非常高的限制,在这种情况下几乎无法达到,但它仍然存在。

如果您只需要知道当前价格而不需要历史记录,您可以使用投影进行查询,以避免通过网络发送庞大的数组:

db.TestC.find({Name: 'P1'}, {Name, CurrentPrice}});

至于加分题​​,可以利用聚合框架:

db.TestC.aggregate([
  {
    $project: {
      Name: 1,
      CurrentPrice: 1,
      PreviousPrice: { // remove this key if you don't need to have previous price in the result
        $arrayElemAt: [
          "$PriceHistory",
          0 // depends on whether you store prices by pushing to the end of history array, or to the beginning of it
        ]
      },
      IsCurrentPriceLower: {
        $lt: [
          "$CurrentPrice",
          {
            $arrayElemAt: [
              "$PriceHistory",
              0 // depends on whether you store prices by pushing to the end of history array, or to the beginning of it
            ]
          }
        ]
      }
    },
  },
  {
    $match: {
      IsCurrentPriceLower: true
    }
  }
])

关于MongoDB 存储和查询价格历史,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55878600/

有关MongoDB 存储和查询价格历史的更多相关文章

  1. ruby - ECONNRESET (Whois::ConnectionError) - 尝试在 Ruby 中查询 Whois 时出错 - 2

    我正在用Ruby编写一个简单的程序来检查域列表是否被占用。基本上它循环遍历列表,并使用以下函数进行检查。require'rubygems'require'whois'defcheck_domain(domain)c=Whois::Client.newc.query("google.com").available?end程序不断出错(即使我在google.com中进行硬编码),并打印以下消息。鉴于该程序非常简单,我已经没有什么想法了-有什么建议吗?/Library/Ruby/Gems/1.8/gems/whois-2.0.2/lib/whois/server/adapters/base.

  2. ruby - 解析 RDFa、微数据等的最佳方式是什么,使用统一的模式/词汇(例如 schema.org)存储和显示信息 - 2

    我主要使用Ruby来执行此操作,但到目前为止我的攻击计划如下:使用gemsrdf、rdf-rdfa和rdf-microdata或mida来解析给定任何URI的数据。我认为最好映射到像schema.org这样的统一模式,例如使用这个yaml文件,它试图描述数据词汇表和opengraph到schema.org之间的转换:#SchemaXtoschema.orgconversion#data-vocabularyDV:name:namestreet-address:streetAddressregion:addressRegionlocality:addressLocalityphoto:i

  3. ruby-on-rails - 在 Rails 和 ActiveRecord 中查询时忽略某些字段 - 2

    我知道我可以指定某些字段来使用pluck查询数据库。ids=Item.where('due_at但是我想知道,是否有一种方法可以指定我想避免从数据库查询的某些字段。某种反拔?posts=Post.where(published:true).do_not_lookup(:enormous_field) 最佳答案 Model#attribute_names应该返回列/属性数组。您可以排除其中一些并传递给pluck或select方法。像这样:posts=Post.where(published:true).select(Post.attr

  4. ruby - Rack:如何将 URL 存储为变量? - 2

    我正在编写一个简单的静态Rack应用程序。查看下面的config.ru代码:useRack::Static,:urls=>["/elements","/img","/pages","/users","/css","/js"],:root=>"archive"map'/'dorunProc.new{|env|[200,{'Content-Type'=>'text/html','Cache-Control'=>'public,max-age=6400'},File.open('archive/splash.html',File::RDONLY)]}endmap'/pages/search.

  5. sql - 查询忽略时间戳日期的时间范围 - 2

    我正在尝试查询我的Rails数据库(Postgres)中的购买表,我想查询时间范围。例如,我想知道在所有日期的下午2点到3点之间进行了多少次购买。此表中有一个created_at列,但我不知道如何在不搜索特定日期的情况下完成此操作。我试过:Purchases.where("created_atBETWEEN?and?",Time.now-1.hour,Time.now)但这最终只会搜索今天与那些时间的日期。 最佳答案 您需要使用PostgreSQL'sdate_part/extractfunction从created_at中提取小时

  6. ruby-on-rails - 为什么在 Rails 5.1.1 中删除了 session 存储初始化程序 - 2

    我去了这个website查看Rails5.0.0和Rails5.1.1之间的区别为什么5.1.1不再包含:config/initializers/session_store.rb?谢谢 最佳答案 这是删除它的提交:Setupdefaultsessionstoreinternally,nolongerthroughanapplicationinitializer总而言之,新应用没有该初始化器,session存储默认设置为cookie存储。即与在该初始值设定项的生成版本中指定的值相同。 关于

  7. ruby-on-rails - 尝试设置 Amazon 的 S3 存储桶 : 403 Forbidden error & setting permissions - 2

    我正在关注Hartl的railstutorial.org并已到达11.4.4:Imageuploadinproduction.我做了什么:注册亚马逊网络服务在AmazonIdentityandAccessManagement中,我创建了一个用户。用户创建成功。在AmazonS3中,我创建了一个新存储桶。设置新存储桶的权限:权限:本教程指示“授予上一步创建的用户读写权限”。但是,在存储桶的“权限”下,未提及新用户名。我只能在每个人、经过身份验证的用户、日志传送、我和亚马逊似乎根据我的名字+数字创建的用户名之间进行选择。我已经通过选择经过身份验证的用户并选中了上传/删除和查看权限的框(而不

  8. ruby-on-rails - solr 清理查询 - 2

    我在Rails上使用带有ruby​​的solr。一切正常,我只需要知道是否有任何现有代码来清理用户输入,比如以?开头的查询。或* 最佳答案 我不知道执行此操作的任何代码,但理论上可以通过查看parsingcodeinLucene来完成并搜索thrownewParseException(只有16个匹配!)。在实践中,我认为您最好只捕获代码中的任何solr异常并显示“无效查询”消息或类似信息。编辑:这里有几个“sanitizer”:http://pivotallabs.com/users/zach/blog/articles/937-s

  9. ruby - 如何打印出 Mechanized 存储的 cookie? - 2

    我正在使用mechanize登录网站,然后检索页面。我遇到了一些问题,我怀疑这是由于cookie中的某些值造成的。当Mechanize登录网站时,我假设它存储了cookie。如何通过Mechanize打印出存储在cookie中的所有数据? 最佳答案 代理有一个cookie方法。agent=Mechanize.newpage=agent.get("http://www.google.com/")agent.cookiesagent.cookies.to_scookie返回一个Mechanize::Cookiesobject

  10. ruby-on-rails - Rails 3 在一个查询中包含多个表 - 2

    我正在为锦标赛开发一个Rails应用程序。我在这个查询中使用了三个模型:classPlayertruehas_and_belongs_to_many:tournamentsclassTournament:destroyclassPlayerMatch"Player",:foreign_key=>"player_one"belongs_to:player_two,:class_name=>"Player",:foreign_key=>"player_two"在tournaments_controller的显示操作中,我调用以下查询:Tournament.where(:id=>params

随机推荐