Php SQL将多行转换为长度可变的单行

Php SQL将多行转换为长度可变的单行,php,sql,mysql,Php,Sql,Mysql,我正在使用MySQL(以及可选的PostgreSQL)为drupal6/PHP5编写一个模块 我有一个MySQL字段表(fid、名称、类型、类…)和一个参数表 引用这些字段(通过“fid”)的值(lid、pid、fid、numval、stringval)。 参数将仅显示数值(浮点/实数)或字符串值(文本),但不显示 两者(根据字段“类型”) 对于给定的“lid”,可以使用多个/可变数量的参数/行 在循环中轻松检索为行。我想做的是检索一个 “值”行,其中每列的标题为相关字段名。 在drupal中,

我正在使用MySQL(以及可选的PostgreSQL)为drupal6/PHP5编写一个模块

我有一个MySQL字段表(fid、名称、类型、类…)和一个参数表 引用这些字段(通过“fid”)的值(lid、pid、fid、numval、stringval)。 参数将仅显示数值(浮点/实数)或字符串值(文本),但不显示 两者(根据字段“类型”)

对于给定的“lid”,可以使用多个/可变数量的参数/行 在循环中轻松检索为行。我想做的是检索一个 “值”行,其中每列的标题为相关字段名。 在drupal中,这样的查询将返回所有field:value对作为object-attribute:value 在一个数据库调用中对,我认为这样会更有效

Google为我找到了一些SQL示例“将多行合并为一行”,但是 它们似乎假定对数据库中固定数量的列/字段进行预先指定的标记 结果集和/或生成列条目作为单个复合“name:value”字符串。 我希望有一种更通用的方法来处理任意数量的数据 字段,这对MySQL和PostgreSQL都有效吗

我只有非常基本的SQL经验,所以我不知道在视图、临时表或动态定义和执行过程方面有什么可能

谢谢

举例来说

FIELDS
FID    NAME       TYPE  CLASS      WIDGET   SIZE   UNITS  DESCRIPTION  .....
 1     voltage   float  instrument   text   10
 2     current   float  instrument   text   10
 3     size      float  sample       text   10
 4     colour    text   sample       text   30
 ...

PARAMS
PID  LID   FID  NUMVAL   STRINGVAL
 1    1     1     2.5      NULL
 2    1     4     NULL    'blue' 
 3    2     1     2.7      NULL
 4    2     2     13       NULL
 5    2     3     27       NULL
 6    2     4     NULL     'greenish blue'
当某些select LID=1表达式返回一行时:

|  voltage  |  colour |
-----------------------
|    2.5    |  'blue' |
然后选择LID=2

|  voltage  | current | size |    colour       |
------------------------------------------------
|    2.7    |  13     |  27  | 'greenish blue' |   

这将垂直显示数据,而不是水平显示数据

SELECT
    FIELDS.NAME AS PROPERTYNAME,
    CASE WHEN PARAMS.NUMVAL IS NULL THEN STRINGVAL ELSE CAST(PARAMS.NUMVAL AS VARCHAR(100)) END AS PROPERTYVALUE
FROM
    PARAMS, FIELDS
WHERE
    PARAMS.FID = FIELDS.FID
        AND
    PARAMS.LID = 1
ORDER BY
    PARAMS.FID

SQL可能需要一些调整,但这是我在不访问DB模式的情况下所能做的最好的了。

透视表的东西似乎太乱了。 我想做一些简单的事情 (感谢John Pick向我展示如何使用用例!):

只需在PHP中使用explode()对“vals”字符串进行后期处理

真是个逃避!我本来希望给出一个更优雅的解决方案 以正确格式返回列所需的所有信息 存在于参数和字段表中。现在我不得不担心斯特林瓦尔
带分隔符:-/

请提供样本数据以及结果的外观。完成。干杯实际上,我希望字段只有大约30行,参数超过一百万。在不同的条件/仪器/用法下,将记录/需要不同的字段。祝贺您,您重新发现了EAV的一个变体。它在大多数关系数据库中往往表现不好。你为什么要把所有数据塞进一个表中?我在两个相关的科学元数据数据库中看到过类似的表结构,所以没有理由认为它特别低效。这些值主要存储为实验的永久记录,而不是用于计算目的的密集访问。基本上,我只希望在Drupal中以表格形式查看数据,可能是50行20列的页面。因此,在我看来,对于一个页面,50 db的请求比1000 db的请求要有效得多。我需要不同数量的参数来记录不同仪器的不同信息,但需要一些公共字段。如果我能在一个SQL过程中隐藏复杂性,尽管效率很低,那对我来说是一种更简单的方法。谢谢。我想我要找的是:“自动化数据透视表查询”
SELECT p.l_id, 
   GROUP_CONCAT(
       CONCAT(f.name,'=', 
          CASE WHEN p.stringval IS NULL
               THEN p.numval 
            ELSE p.stringval 
          END
       ) SEPARATOR '||'
   ) AS vals 
 FROM
    params AS p 
 LEFT JOIN fields AS f 
    ON  p.f_id=f.f_id 
 WHERE 
    p.l_id=1 
 GROUP BY 
    p.l_id;
+------+---------------------------------------------------------- ... -+
| l_id | vals                                                           |
+------+---------------------------------------------------------- ... -+
|    1 | kv=50||ma=50||pressure=0||temp_ccd=-58||temp_sample=150|| ...  |
+------+---------------------------------------------------------  ...  +