Php 需要算法或MySQL查询建议

Php 需要算法或MySQL查询建议,php,mysql,algorithm,performance,memory,Php,Mysql,Algorithm,Performance,Memory,我迫切需要算法或查询构造帮助 我们有一个用户生成的灵活数据库,它是使用我们创建的表单生成器创建的。这些表单的数据存储在两个表中,如下所示: instances表告诉我们用户正在查看的表单,然后instance_records表包含该实例的所有数据。field_id列告诉我们数据映射到表单上的哪个字段。我们使用这样一个表而不是为每个表单创建一个表的原因是MySQL限制了表中的列数,因为数据是有效长度的varchar。一种可能是对数据使用文本字段,但这样我们就会失去内置的MySQL搜索功能 在基本

我迫切需要算法或查询构造帮助

我们有一个用户生成的灵活数据库,它是使用我们创建的表单生成器创建的。这些表单的数据存储在两个表中,如下所示:

instances表告诉我们用户正在查看的表单,然后instance_records表包含该实例的所有数据。field_id列告诉我们数据映射到表单上的哪个字段。我们使用这样一个表而不是为每个表单创建一个表的原因是MySQL限制了表中的列数,因为数据是有效长度的varchar。一种可能是对数据使用文本字段,但这样我们就会失去内置的MySQL搜索功能

在基本形式上工作得很好,速度也很快。问题是表单的一个实例可以引用表单的另一个实例。例如,我们有一个名为约会的用户创建的表单。在该表单上,它是指患者表单、技师表单、医生表单等

因此,在具有实例id的预约表单上,患者字段的值实际上是患者的实例id,医生字段的值是医生的实例id,等等。在第一级引用中,情况并不太糟糕。但是,您可以拥有参考链。我可以有一个处方,它引用了一个病人的预约,等等。因此,如果我想获得处方上病人姓名的值,我必须沿着链向下,为数据获取正确的实例id和字段id

因此,如果我想做一份预约报告,并显示患者姓名、医生姓名和技师姓名,我必须经历一些困难。我尝试的是创建视图,然后将视图连接到显示查询所有数据的最终视图。但是,它消耗了大量内存,并开始将视图临时表写入磁盘,速度非常慢。使用查询缓存,报表第二次运行时,速度非常快。但是,一旦我们获得5000-7000个以上的实例,第一次运行可能需要一分钟


在我的脑海里,有一件事让我觉得很痒,那就是可能有某种方式来存储数据,我可以利用一些更快的树搜索算法

听起来像是在数据库中创建数据库。我在找一个dailywtf链接

无论如何,听起来你需要一张预约表、一张病人表、一张医生表和一张技师表,然后你需要将它们正确地连接起来

例如,要查看昨天预约的患者、医生和技术人员,您可以这样做

SELECT 
  Appointment.start-time 
  Appointment.end-time 
  Patient.name 
  Patient.insurance-carrier 
  Doctor.name 
  Tech.name 
  Tech.home-lab
FROM Appointment
JOIN Patient on Appointment.patient-id = Patient.patient-id
JOIN Doctor on Appointment.doctor-id = Doctor.doctor-id
JOIN Tech on Appointment.tech-id = Tech.tech-id
WHERE Appointment.appointment-date = $YESTERDAY
编辑:让我们给出具有可变字段数的患者示例

表Patient-包含所有患者的数据

| ID   |    Name     | Insurance Carrier | .. other fields
+------+-------------+-------------------+-------
+ 0001 | John Doe    | ABC Healthcare    |
+ 0002 | Jane Doe    | ABC Healthcare    |
+ 0003 | Jon Skeet   | C# Insurance Inc. |
+ 0004 | Mark Byers  | Gold Badge Health |
+------+-------------+-------------------+-------
表格病人表格

| Form-Name |    Form-Field    | Required | Default-Value |
+-----------+------------------+----------+---------------|
| Vitals    | Blood Pressure   | TRUE     | null          |
| Vitals    | Pulse            | TRUE     | null          |
| Vitals    | Ear Temperature  | FALSE    | null          |
| Lab Work  | Lab Room         | TRUE     | Lab-001       |
| Lab Work  | Technician       | TRUE     | null          |
| Lab Work  | Insurance Covers | TRUE     | NO            |
| Payment   | Balance          | TRUE     | $0.00         |
| Payment   | Co-Pay           | FALSE    | 0.00%         |
| Payment   | Deductable       | FALSE    | $0.00         |
| Payment   | Payment Terms    | FALSE    | 30 Days Full  |
+-----------+------------------+----------+---------------|
Table Patient Form(表格患者表单)字段-包含患者可能可用或不可用的数据

| Patient-ID | Form-Name |    Form-Field    | Form Value |
+------------+-----------+------------------+------------+
+ 0001       | Vitals    | Blood Pressure   | 130 / 54   |
+ 0001       | Vitals    | Pulse            | 84bpm      |
+ 0001       | Vitals    | Ear Temperature  | 98.4F      |
+ 0002       | Vitals    | Blood Pressure   | 126 / 74   |
+ 0002       | Vitals    | Pulse            | 87bpm      |
+ 0002       | Vitals    | Ear Temperature  | 99.0F      |
+ 0003       | Lab Work  | Lab Room         | SO-Meta    |
+ 0003       | Lab Work  | Technician       | Rose Smith |
+ 0003       | Lab Work  | Insurance Covers | TRUE       |
+ 0003       | Vitals    | Blood Pressure   | 190 / 100  |
+ 0003       | Vitals    | Pulse            | 213bpm     |
+------------+-----------+------------------+------------+
您现在可以这样查询:

SELECT 
  Patient.name 
  Patient-form-field.form-name 
  Patient-form-field.form-field 
  Patient-form-field.form-value
FROM Patient
JOIN Patient-Form-Field on ( Patient.patient-id = patient.id 
                         AND Patient-form-field in ("Vitals","Lab Work")
                           )
WHERE Patient.patient-id IN ("0001","0002","0003")

你应该仔细阅读EAV。。。它讨论了存储值的两种不同方法。无论采用哪种方法,最终都会得到对任何给定表单的一个查询,该查询基本上会获取主实体(在本例中为表单)的所有值。然后,在应用程序端或数据库端,将这些值适当地聚合在一起,以供应用程序使用


表单本身应该是一个具有字段列表的单个原子单元,您不需要存储字段实际来自哪个表单,只需要将其作为字段存储在完整表单上。在创建过程中,您应该在应用程序端开发将字段合并到单个表单的逻辑。

有人对从数据库检索报告引用数据的有效方法有什么想法吗?硬编码表不是一个选项。该应用程序特别允许用户创建自己的表单和业务逻辑。Zoho creator也有类似的能力,这不是问题。让应用程序也创建与其关联的表。然后为他们提供一种机制来匹配创建一些查询(使用一些查询构建应用程序或其他东西)。glowcode-请注意我的声明,基于MySQL的行大小限制,无法创建包含所有字段的表。这就是促使我选择这个更复杂模型的原因。:-)MySQL行上允许8025字节的限制。你是说预约、医生和病人都有那么多数据?我简直不敢相信。我可以看到他们的总体情况,但不是每个人。如果您的应用程序为每种类型(如RDBMS)创建一个表,您将获得所需的应用程序性能。不,我想说的是,我们不知道每个表将有多少列数据。患者可以在表单上有10个字段或1000个字段。我们不知道。因此,如果您有多个varchar列允许文章条目,那么在某个时候您可以(并且确实)达到行大小的限制。我们的许多表格都是医学问卷,有数百个动态生成的问题。这是绝对正确的,我同意后处理可能是我最好的选择。但是,我还没有找到一种优雅的方法来做到这一点,并将分页和排序牢记在心。谢谢你的链接。它至少为我提供了更多的搜索术语。如果您扩展字段的数据模型,为一些与查询无关的元数据(可能存储为序列化php数组或json字符串)创建一个列,那么您可以在需要时存储字段元数据,如视图配置(字段集、标签等)。。。就搜索或排序结果集而言,这些内容实际上并不重要。。。它只是用来确定输出结构的元数据……如果你要做后期处理,为什么还要麻烦数据库呢?