计数系统设计

news/2024/10/23 9:14:13/文章来源:https://www.cnblogs.com/wxwall/p/18494386

在营销的场景里有三要素

  1. 用户
  2. 商品
  3. 优惠

在这三个要素里,再加一些如时间,数量,频次等变量,会演化出各种组合,使得业务变得非常灵活。各业务线为了满足业务,一般都会各自实现,且多数情况下都会重复实现,而且实现起来各地方都会产生交叉配置,交叉互斥的问题。在观察到这些问题后,总结并尝试用一个计数频次中间件形态的系统统一解决。一是解决了复杂度、重复建设;二是统一处理后,数据层面上将整体打通,对于用户监控、风控、特征、行为上提供完整数据。

在电商的系统中,有商品、用户、优惠三种要素。这三种要素分别在数量,时间,频次上又有多维度的分类。
如商品限量100份(数量)对用户每天(时间)每人购买限量2份(频次),按这种规律下,用户使用优惠也同样遵循这种规则,即
优惠券总数100张(数量),用户每场(时间)可使用1张(频次)
抽奖优惠也一样,即
优惠总数100张,用户每天(时间)可领取1张(频次)
发放优惠也一样,即
优惠总额100元,用户每天(时间)可优惠1次(频次)


分类法

  1. 按主体,维度分类
主体\维度 数量 时间 频次
商品 总数 指定周期,天,小时,周 不限,1份,多份
用户 总数 指定周期,天,小时,周 不限,1份,多份
优惠 总数 指定周期,天,小时,周 不限,1份,多份
活动 总数 指定周期,天,小时,周 不限,1份,多份

按上面这个分类,主体会变,维度会变,先设计领域模型,分别为实体(entity);维度(dimensions);实体维度关系(entityDimensionsRel),关系领域将表示,主体将拥有多个维度,并在多个维度中设定维度值,如商品每天限购1份,那么将在entityDimensionsRel中的limit_value中设定1,time_interval设定为1天

领域模型

数据模型

数据库表模型

  1. 主体表 (Entities)
  • EntityID: 主键,唯一标识某个主体(如商品、优惠、活动等)
  • EntityType: 主体类型(如商品、优惠、抽奖等)
  • EntityName: 主体名称
CREATE TABLE Entities (EntityID INT PRIMARY KEY,EntityType VARCHAR(50),EntityName VARCHAR(100)
);
  1. 维度定义表 (Dimensions)
  • DimensionID: 主键,唯一标识某个维度(如数量、时间、频次)
  • DimensionName: 维度名称(如“数量”、“时间”、“频次”)
  • DimensionType: 维度类型(如整数、日期、时间区间等)
CREATE TABLE Dimensions (DimensionID INT PRIMARY KEY,DimensionName VARCHAR(50),DimensionType VARCHAR(50)
);
  1. 主体-维度关系表 (EntityDimensions)
  • EntityDimensionID: 主键,唯一标识某个主体-维度关系
  • EntityID: 外键,关联到Entities表
  • DimensionID: 外键,关联到Dimensions表
  • LimitValue: 该维度的限制值(如限量、限次等)
  • TimeInterval: 时间间隔(如每天,每场活动等),适用于时间维度
CREATE TABLE EntityDimensions (EntityDimensionID INT PRIMARY KEY,EntityID INT,DimensionID INT,LimitValue INT,TimeInterval VARCHAR(50),FOREIGN KEY (EntityID) REFERENCES Entities(EntityID),FOREIGN KEY (DimensionID) REFERENCES Dimensions(DimensionID)
);

上面这些表可以完整记录主体在各维度的限制值。还需要一张实时记录主体数据在各维度的过程数据

  1. 实例数据记录表 (EntityDimensionRecords)
  • RecordID: 主键,唯一标识某条记录
  • EntityID: 外键,关联到Entities表
  • DimensionID: 外键,关联到Dimensions表
  • UserID: 外键,关联到用户表(适用时)
  • Value: 在该维度上记录的数值
  • RecordDate: 记录的日期或时间。
CREATE TABLE EntityDimensionRecords (RecordID INT PRIMARY KEY,EntityID INT,DimensionID INT,UserID INT,Value INT,RecordDate DATETIME,FOREIGN KEY (EntityID) REFERENCES Entities(EntityID),FOREIGN KEY (DimensionID) REFERENCES Dimensions(DimensionID)
);

数据流转

样例1

用户参与大转盘活动,活动周期内只能抽一次奖

主体:大转盘活动

维度:时间,计数

关系:限制值(一次);限制时间(活动周期);

简单填入数据,业务就可以满足了。

现在又有新的业务需求,即这个活动周期为1个月,用户每天都要能参与一次,现有的表模型就不支持了!

关系表(EntityDimensions)的时间字段TimeInterval是个varchar,表示1天、1小时等枚举值是可以,如果表示时间段,每天等带频次的复杂时间是不够的,所以,最好的办法之一就是将时间维度拆出一张表

CREATE TABLE TimePeriods (TimePeriodID INT PRIMARY KEY,PeriodName VARCHAR(50),       TimeInterval VARCHAR(50),     -- 时间周期(每天、每小时、每半小时、每分钟)StartTime TIME,               -- 时间段开始时间EndTime TIME                  -- 时间段结束时间
);

有了这张表后,就可以表示周期时间段的计数关系了。

有了这张表后,业务在查询EntityDimensionRecords,就知道这条记录的周期,开始时间结束时间。

如果时间频次TimeInterval是天,当前时间为2022-12-12时,EntityDimensionRecords.RecordDate值为2022-12-11时,那么EntityDimensionRecords需要重新生成一条记录,并且RecordDate值为2022-12-12;

越往深入,能够枚举出的维度是有限的,在大的方向上,每一个维度也可以拆分出一个领域也是可行的。因为维度值不一样,单纯用维度一个变量有点满足不了需求,如时间维度和数量维度,维度值用一个变量就表示不了,时间范围最少需要2个字段。所以在不同的业务发展时期,只有当时最合适的设计,没有永远对的设计。在考虑扩展性的同时,也需要考虑研发成本。


如果以后有需求对计数的方式有变化,比如一次计数消耗2次机会,那相应的,再在EntityDimensions.LimitValue字段上做一个新表来表示计数的复杂方式。万变不离其宗,好的设计一定是支持业务慢慢成长起来的。糟糕的设计是不停的妥协设计,随着时间推移开发和维护将会越来越困难!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/819502.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

PbootCMS授权码可以更换域名吗? 授权码丢失怎么办?

授权码可以更换域名吗?不可以:授权码是绑定特定域名的,如果需要更换域名,建议重新获取新的授权码。授权码丢失怎么办?重新获取:如果授权码丢失,可以重新访问授权页面,输入相同的域名再次获取授权码。扫码添加技术【解决问题】专注中小企业网站建设、网站安全12年。熟悉…

PbootCMS授权码是否可以用于不同域名的子域名?是否可以用于不同域名的子目录?

授权码是否可以用于不同域名的子域名?不可以:授权码是绑定特定域名的,不支持不同域名的子域名。例如,sub1.example.com 和 sub2.anotherdomain.com 需要分别获取授权码。18. 授权码是否可以用于不同域名的子目录?不可以:授权码是绑定特定域名的,不支持不同域名的子目录。…

PbootCMS验证码不显示或显示不清楚怎么办

验证码不显示或显示不清楚问题描述:后台登录时验证码不显示或显示不清楚。 解决方案:避免使用中文路径:确保所有文件和目录名称均为英文或数字。 切换PHP版本:推荐使用PHP 7.3、7.2、5.6版本。 检查文件权限:确保验证码相关文件和目录具有适当的读写权限(通常为755或644)…

值得信赖的FTP替代方案有哪些,一文带你详细了解!

FTP(文件传输协议)因其传输速度慢、安全隐患、管理复杂性、稳定性不足以及审计难题等缺陷,使得企业在寻找更高效的替代方案时显得尤为迫切。 FTP替代方案有哪些,简单了解看下吧: 1、SFTP:SFTP是建立在SSH(Secure Shell)协议之上的文件传输协议,提供了数据传输的加密和…

HTTP 2.0 新特性

HTTP 2.0 新特性HTTP 2.0 为什么使用二进制分帧?二进制协议比文本协议更加紧凑,减少占用空间 分帧层相当于将 HTTP 切分,更加灵活,比如可以对 header 帧做单独的特殊处理 分帧层有着属于自己的报文头,其中的 Stream Identity 使得操作系统具备将多个响应以及请求一一匹配的…

Python脚本检测笑脸漏洞

Python脚本检测笑脸漏洞 一、漏洞介绍 ​ vsftpd2.3.4中在6200端口存在一个shell,使得任何人都可以进行连接,并且VSFTPD v2.3.4 服务,是以 root 权限运行的,最终我们提到的权限也是root;当连接带有vsftpd 2.3.4版本的服务器的21端口时,输入用户中带有“😃 ”,密码…

Veritas Backup Exec 24.0 发布,新增功能概览

Veritas Backup Exec 24.0 发布,新增功能概览Veritas Backup Exec 24.0 发布,新增功能概览 Veritas Backup Exec 24.0 (Windows) - 面向中小型企业的数据备份和恢复 请访问原文链接:https://sysin.org/blog/veritas-backup-exec-24/ 查看最新版。原创作品,转载请保留出处。…

slope trick

slope trickP4597 序列 sequence 首先考虑 \(dp\) 。 由于只需将序列改为非严格递增,那么就有一个贪心,即最终答案的数集不会变大。 为什么呢? 这是因为只有序列某一位置严格递减时,才会进行修改。 修改可以将前面的数降到和后面的数一样大,或者将后面的数提到和前面的数一…

黄绿题选刷

[ABC376D] Cycle找到包含节点 1 的环,直接从节点一出发,BFS,如果第二次遍历到了节点1,直接输出时间即可。点击查看代码 #include <bits/stdc++.h> using namespace std; #define FOR(i, a, b) for (int i = (a); i <= (b); ++i) #define ROF(i, a, b) for (int i …

面试题:如何能够保证T2在T1执行完后执行,T3在T2执行完后执行?——CountDownLatch原理

CountDownLatch的使用方式 CountDownLatch用于某个线程等待其他线程执行完任务再执行,与thread.join()功能类似。常见的应用场景是开启多个线程同时执行某个任务,等到所有任务执行完再执行特定操作,如汇总统计结果。 面试题:如何能够保证T2在T1执行完后执行,T3在T2执行完后…

读数据工程之道:设计和构建健壮的数据系统17存储的原材料

存储的原材料1. 存储 1.1. 存储是数据工程生命周期的基石1.1.1. 是数据获取、转换和服务主要阶段的基础1.1.1.1. 当构建数据管道时,随着数据经过获取、转换和服务阶段,工程师会选择适当的抽象来存储他们的数据1.1.2. 当数据在生命周期中移动时,它会被多次存储1.1.2.1. 必须在…

JAVA 前三次题目集总结

在过去的一个月里完成了java的前三次大作业对于JAVA的语法以及面向对象编程还不台上手,接下来说前三次大作业。 前三次大作业要是围绕答题判题系统展开的每次作业都在完善这个程序的功能可以说 1.第一次作业判分功能 在第一次作业阶段,核心任务是建立一个能够接收题目信息和答…