首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >用于在列中显示行数据的SQL

用于在列中显示行数据的SQL
EN

Stack Overflow用户
提问于 2015-04-24 12:22:52
回答 4查看 904关注 0票数 20

这是我的sql (在mysql表中)

代码语言:javascript
运行
复制
select * from(SELECT sample_register.usin,    
                     DATE_FORMAT(sample_register.doc,'%d-%m-%Y') as doc1,    
                     sample_register.location,    
                     sample_register.description,    
                     sample_register.type,    
                     sample_allocation.gamma,    
                     gamma_results.act,    
                     gamma_results.act_sd,    
                     gamma_results.mdl,    
                     gamma_results.bdl,    
                     DATE_FORMAT(count_dt,'%d-%m-%Y') as count_dt    
               FROM sample_register    
               LEFT JOIN sample_allocation    
               ON sample_register.usin=sample_allocation.usin    
               LEFT JOIN gamma_results    
               ON gamma_results.usin = sample_register.usin    
               AND gamma_results.istp='Cs137'    
               WHERE mid(sample_register.usin,3,1)='F'    
               AND sample_register.doc BETWEEN '2015-01-01'    
                                       AND '2015-03-31'    
                                       AND sample_register.category='ter'    
                                       AND sample_allocation.gamma='Y'    
               ORDER BY mid(sample_register.usin,3,1),    
                        sample_register.doc,    
                        sample_register.usin) AS a    
               LEFT JOIN (SELECT sample_register.usin,    
                                 gamma_results.act,    
                                 gamma_results.act_sd,    
                                 gamma_results.mdl,    
                                 gamma_results.bdl    
                          FROM sample_register    
                          LEFT JOIN gamma_results    
                          ON gamma_results.usin = sample_register.usin    
                          AND gamma_results.istp='k40'    
                          WHERE mid(sample_register.usin,3,1)='F'    
                          AND sample_register.doc    
                          BETWEEN '2015-01-01'    
                          AND '2015-03-31'    
                          AND (sample_register.category='ter')    
                          ORDER BY mid(sample_register.usin,3,1),    
                                   sample_register.doc,    
                                   sample_register.usin) AS b    
               ON a.usin=b.usin

gamma_results表中有4条记录。2015年10月4日和2015年4月18日各有两项记录。

代码语言:javascript
运行
复制
USIN        istp     act     count_dt
-----------------------------------------
15FML002    Cs137   0.00769  10/04/15
15FML002    K40     0        10/04/15
15FML002    Cs137   0.00608  18/04/15
15FML002    K40     12.117   18/04/15

以下形式查询输出数据(为方便起见,我删除了一些字段)

代码语言:javascript
运行
复制
15FML002            0.00769 Y   10/04/15    00
15FML002            0.00769 Y   10/04/15    12.117
15FML002            0.00608 Y   18/04/15    00
15FML002            0.00608 Y   18/04/15    12.117

但是我想在两个记录中获得输出。就是这样的

代码语言:javascript
运行
复制
15FML002            0.00769 Y   10/04/15    00
15FML002            0.00608 Y   18/04/15    12.117

如何重新框住(连接或联合)查询以获得如下输出?/编辑于2015年4月30日

我无法创建一个sqlfiddle,因为在他们的网站上的一些问题。下面是两个表sample_register和gamma results的DDL和DML。此时可以忽略sample_allocation表。

代码语言:javascript
运行
复制
CREATE TABLE `sample_register` (
  `usin` varchar(11) NOT NULL,
  `sample_id` varchar(7) NOT NULL,
  `doc` date NOT NULL,
  `location` varchar(255) DEFAULT NULL,
  `category` varchar(50) DEFAULT NULL,
  `type` varchar(255) DEFAULT NULL,
  `description` varchar(255) DEFAULT NULL,
  `fwt` decimal(10,2) DEFAULT NULL COMMENT 'This filed contains either fwt in gms or volume in ltr for milk or volume of air for particulate',
  `dwt` decimal(10,2) DEFAULT NULL,
  `ashwt` decimal(10,2) DEFAULT NULL,
  `user` varchar(255) DEFAULT NULL,
  `to_dt` date DEFAULT NULL COMMENT 'This is for particulate sample filter removal date',
  `wc` decimal(10,2) DEFAULT NULL,
  `oc` decimal(10,2) DEFAULT NULL,
  `ac` decimal(10,2) DEFAULT NULL,
  `status` varchar(1) DEFAULT NULL,
  `remarks` varchar(255) DEFAULT NULL,
  PRIMARY KEY (`usin`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1;
INSERT INTO `sample_register` VALUES ('15FML002', 'NIL', '2015-04-09', 'MALLAPUR', 'ter', 'MILK', 'milk', '2000.00', null, null, '1604015', null, null, null, null, null, null);
DROP TABLE IF EXISTS `gamma_results`;
CREATE TABLE `gamma_results` (
  `usin` varchar(255) NOT NULL,
  `sysid` varchar(255) NOT NULL,
  `count_time` decimal(10,0) DEFAULT NULL,
  `geo` varchar(255) DEFAULT NULL,
  `vol` decimal(10,2) DEFAULT NULL,
  `energy` decimal(10,2) DEFAULT NULL,
  `istp` varchar(255) DEFAULT NULL,
  `bkg` decimal(10,5) DEFAULT NULL,
  `eff` decimal(10,3) DEFAULT NULL,
  `sigma` decimal(10,5) DEFAULT NULL,
  `ncps` decimal(10,5) DEFAULT NULL,
  `sd` decimal(10,5) DEFAULT NULL,
  `mdl` decimal(10,5) DEFAULT NULL,
  `act` decimal(10,5) DEFAULT NULL,
  `act_sd` decimal(10,5) DEFAULT NULL,
  `bdl` varchar(1) DEFAULT NULL,
  `entry_time` datetime DEFAULT NULL,
  `entered_by` int(11) DEFAULT NULL,
  `count_dt` date DEFAULT NULL
) ENGINE=MyISAM DEFAULT CHARSET=latin1;
INSERT INTO `gamma_results` VALUES ('15FML002', 'HPGE2', '25000', 'nb', '1000.00', '364.48', 'I131', '0.01000', '3.400', '0.00190', '-0.01000', '0.00041', '0.06882', null, '0.00000', 'Y', '2015-04-13 10:24:11', '1619381', '2015-04-10');
INSERT INTO `gamma_results` VALUES ('15FML002', 'HPGE2', '25000', 'nb', '1000.00', '661.66', 'Cs137', '0.00020', '2.060', '0.00027', '-0.00020', '0.00006', '0.00769', null, '0.00000', 'Y', '2015-04-13 10:24:57', '1619381', '2015-04-10');
INSERT INTO `gamma_results` VALUES ('15FML002', 'HPGE2', '25000', 'nb', '1000.00', '1460.73', 'K40', '0.00500', '0.911', '0.00134', '-0.00450', '0.00032', '1.37855', null, '0.00000', 'Y', '2015-04-13 10:25:37', '1619381', '2015-04-10');
INSERT INTO `gamma_results` VALUES ('15FML002', 'HPGE2', '15000', 'nb50', '2000.00', '661.66', 'Cs137', '0.00020', '3.380', '0.00035', '-0.00020', '0.00006', '0.00608', null, '0.00000', 'Y', '2015-04-20 10:21:48', '1619381', '2015-04-18');
INSERT INTO `gamma_results` VALUES ('15FML002', 'HPGE2', '15000', 'nb50', '2000.00', '1460.73', 'K40', '0.00500', '1.550', '0.00173', '0.04008', '0.00176', '0.52302', '12.11700', '0.53200', 'N', '2015-04-20 10:23:00', '1619381', '2015-04-18');
EN

回答 4

Stack Overflow用户

发布于 2015-04-30 21:56:46

我以前见过这样的输出。

这是由连接中的一个小错误引起的。如果我没记错的话,我通过嵌套我的一些连接作为子查询解决了这个问题,所以我沿着连接将每个表添加到现有的表中。我可能过多地混合了,但它确实工作得很好。(更新:是的,我现在明白了,这正是您正在做的事情)。

在某些情况下,连接并不是唯一的,或者您安排连接的方式也不是唯一的,因此SQL为您提供了它所能提供的所有组合。

(当然,假设让事情变得糟糕的不只是一个丢失的GROUP BY。这是类似问题的另一个来源。)

我会仔细检查一下你的SQL,看看我是否能发现问题所在,但稍微试错一下会快得多。

更新1:这要么是一个令人印象深刻的黑客攻击,要么是一个错误,我无法理解是哪一个。

代码语言:javascript
运行
复制
LEFT JOIN gamma_results    
ON gamma_results.usin = sample_register.usin    
AND gamma_results.istp='Cs137' 

我从来没有见过条件作为连接的一部分。我不能告诉您这是否有效,但我的直觉反应是希望将其放在WHERE子句中。请随时带我去学校,因为你似乎知道你在做什么,而我并没有实际的项目(我也不是什么都知道)。

更新2:鉴于您的硬编码连接必须接近正常工作,我的感觉是我希望在嵌套的SELECT中使用GROUP by,因为您正在使用聚合函数(count)。

我记得有一次做了一个相当复杂的查询,当你深入到它的时候,实际上是说"for each table_a add table_b“。诚实地与GROUP BY交朋友,如果这不能解决你的问题,那么我就是一只无伤大雅的小猴子。

票数 8
EN

Stack Overflow用户

发布于 2015-04-25 22:13:48

首先,如果您需要查询某个特定数据集的帮助,您应该提供相同的数据和sqlfiddle。

由于我没有小提琴的数据,下面是我的猜测:

代码语言:javascript
运行
复制
SELECT sample_register.usin,    
     DATE_FORMAT(sample_register.doc,'%d-%m-%Y') as doc1,    
     sample_register.location,    
     sample_register.description,    
     sample_register.type,    
     sample_allocation.gamma,    
     gr.act,    
     gr.act_sd,    
     gr.mdl,    
     gr.bdl,    
     gr.count_dt,
     grK40.act  
FROM sample_register    
INNER JOIN sample_allocation    
ON sample_register.usin=sample_allocation.usin
   AND sample_allocation.gamma='Y'
LEFT JOIN (
   SELECT
       usin,
    act,    
    act_sd,    
    mdl,    
    bdl,
    count_dt,
    DATE_FORMAT(count_dt,'%d-%m-%Y') as count_dt_formatted    
   FROM gamma_results    
   WHERE istp='Cs137'
) gr
ON gr.usin = sample_register.usin
LEFT JOIN gamma_results grK40   
 ON grK40.usin = gr.usin
    AND grK40.istp='k40'
    AND grK40.count_dt = gr.count_dt
WHERE mid(sample_register.usin,3,1)='F'    
AND sample_register.doc BETWEEN '2015-01-01' AND '2015-03-31'    
   AND sample_register.category='ter'    
ORDER BY mid(sample_register.usin,3,1),    
    sample_register.doc,    
    sample_register.usin

但这只是一种猜测,因为它在我看来非常奇怪。

你写道:

gamma_results表中有4条记录。分别为10/04/2015和18/04/2015的两个记录。:istpact,,USIN count_dt,但在您的查询中使用act,act_sd,mdl,bdl,DATE_FORMAT(count_dt,'%d-%m-%Y') as count_dt,因此我们可以假设您在那里有一些其他列,如:act_sd,mdl,bdl

下面写道:查询输出数据,格式如下(为了方便起见,我删除了一些字段)

代码语言:javascript
运行
复制
15FML002            0.00769 Y   10/04/15    00
15FML002            0.00769 Y   10/04/15    12.117

即使删除了一些字段,这里又有哪些字段?

逻辑上是:usin,act,未知,count_dt,未知(当istp='K40'时等于act )。但这是不可能的,因为您的查询请求中没有这样的字段。在我看来,所提供输出是作为其他查询的结果而获得的,而不是您向我们显示的查询。

但到目前为止,我的猜测是这样的。如有任何问题,欢迎光临。

票数 4
EN

Stack Overflow用户

发布于 2015-05-02 13:10:53

您编写的每个表都应该有一个PRIMARY KEY。这在关系数据库中是一个非常重要的概念。虽然您在sample_register中有PRIMARY KEY,但在gamma_results中没有。

如果你有一个主键,这就是在公园里散步(相对而言)

假设您有以下行:

代码语言:javascript
运行
复制
15FML002            0.00769 Y   10/04/15    00
15FML002            0.00769 Y   10/04/15    12.117
15FML002            0.00608 Y   18/04/15    00
15FML002            0.00608 Y   18/04/15    12.117

假设这些实际上是数据库中不同行的副本,分配主键将创建一个新列,该列将使您的数据如下所示:

代码语言:javascript
运行
复制
1          15FML002            0.00769 Y   10/04/15    00
1          15FML002            0.00769 Y   10/04/15    12.117
2          15FML002            0.00608 Y   18/04/15    00
2          15FML002            0.00608 Y   18/04/15    12.117

对于您的示例来说,这有点过于简单化了,考虑到在问题内部的解释中,您声明了

对于每个USIN,单个count_dt上的istp有两个不同的值。因此,在每个计数日期,一个USIN将有两个记录,其中一个为istp='k40‘,另一个为istp=cs137。因为USIN和count date很常见,所以我想在一行中显示它。然后,如果一个USIN有多个(比如‘n')计数日期,那么就会有nx2记录。但我只需要n行。

我知道您理解这些数据是如何组合在一起的,但是如果您能够告诉SQL数据库这些数据是如何以它所理解的语言组合在一起的,那么您的SQL查询就会变得更加清晰和整洁。

了解主键的去向将帮助您更好地从逻辑上理解表结构。如果您不能分配主键,这意味着表可能需要拆分成块。这一个当然可以从一些标准化中受益。

显然,您在USIN上具有1:n关系,这在这里得到了很好的表示,但您在istp上也具有1:2关系。这不会反映在不同的表中,而是全部反映在同一个表中,这意味着当USINcount_dt的组合完全相同时,它们会在整个表中重复两次。

我并不是说你不能让这个查询工作。您所需要做的就是在底部粘贴一个GROUP BY。但是,在没有索引的情况下,表的执行速度将非常慢。即使有了索引,它也会比需要的速度慢!重要的是,如果没有PRIMARY KEY,你的SQL数据库将会做比它需要的更多的工作。

理想的方式

如果您将表一分为二,为每个USIN/count_dt对提供一个新的PRIMARY KEY,然后创建另一个满足您的istp='k40'istp=cs137需求的表,那么您将只需要在已经很长的查询中额外编写一行查询,这通常会为您节省大量查询时间。

代替SELECT * FROM tableA LEFT JOIN tableB on tableA.USIN=tableB.USIN...,你可以这样写:

代码语言:javascript
运行
复制
SELECT * FROM tableA
LEFT JOIN tableB on tableA.USIN=tableB.USIN
LEFT JOIN tableX on tableB.id = tableX.tableB_id
....

您应该最终得到相同的数据集。如果你只想要唯一的值,你需要做的就是去掉第二个JOIN

如果您不能更改表结构

如果由于某种原因不能更改表结构,那么您可以选择创建一个由USINcount_dtistp组成的复合主键,因为它们应该是唯一的,并且应该只在表中以特定的组合出现一次。这可以很快地扩展,但应该会给你大体的要点。

要使用此方法创建不同的值,您应该在USINcount_dt上有一个复合索引,然后使用GROUP BY USIN, count_dt

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/29838659

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档