如果你能解决这个问题,我将非常感激。
我有这个Oracle SQL查询的结果,是关于夜班时间表的。
start_day_hours是班次start_date和午夜之间的总工作时间。 end_day_hours是午夜和轮班结束之间的总工作时间。
start midnight end start_day_hours end_day_hours
02/10/17 21:33 02/10/17 23:59 03/10/17 00:42 2,43 0,71
03/10/17 21:34 03/10/17 23:59 04/10/17 00:19 2,42 0,32
04/10/17 21:59 04/10/17 23:59 05/10/17 55:36 2,00 0,92
16/10/17 21:59 16/10/17 23:59 17/10/17 00:01 2,00 0,01
18/10/17 22:50 18/10/17 23:59 19/10/17 00:25 1,16 0,42
19/10/17 22:19 19/10/17 23:59 20/10/17 01:00 1,67 1,01
我需要白天的start_day_hours和end_day_hours的总和,如:
day total_hours
02/10/17 2,43 (2,43)
03/10/17 3,13 (0.71+2,42)
04/10/17 2,32 (0.32+2.00)
05/10/17 0,92 (0,92)
16/10/17 2,00 (2,00)
17/10/17 0,01 (0,01)
18/10/17 1,16 (1,16)
19/10/17 2,51 (0.42+1.67)
20/10/17 1,01 (1,01)
非常感谢你的帮助!
答案 0 :(得分:1)
Oracle 11g R2架构设置:
CREATE TABLE shift (
"start" DATE,
"end" DATE
);
INSERT INTO shift
SELECT TIMESTAMP '2017-10-02 21:33:00', TIMESTAMP '2017-10-03 00:42:00' FROM DUAL UNION ALL
SELECT TIMESTAMP '2017-10-03 21:34:00', TIMESTAMP '2017-10-04 00:19:00' FROM DUAL UNION ALL
SELECT TIMESTAMP '2017-10-04 21:59:00', TIMESTAMP '2017-10-05 00:55:00' FROM DUAL UNION ALL
SELECT TIMESTAMP '2017-10-16 21:59:00', TIMESTAMP '2017-10-17 00:01:00' FROM DUAL UNION ALL
SELECT TIMESTAMP '2017-10-18 22:50:00', TIMESTAMP '2017-10-19 00:25:00' FROM DUAL UNION ALL
SELECT TIMESTAMP '2017-10-19 22:19:00', TIMESTAMP '2017-10-20 01:00:00' FROM DUAL;
查询1 :
使用行生成器在最早的start
和最新的end
之间获取每一天,然后在当天与班次重叠并将这些重叠聚合时将其加入原始表:
WITH days ( dt ) AS (
SELECT min_dt + LEVEL - 1
FROM (
SELECT TRUNC( MIN( "start" ) ) AS min_dt,
TRUNC( MAX( "end" ) ) AS max_dt
FROM shift
)
CONNECT BY min_dt + LEVEL - 1 <= max_dt
)
SELECT dt,
SUM(
LEAST( "end", dt + INTERVAL '1' DAY )
- GREATEST( "start", dt )
) * 24 AS hours_worked
FROM shift s
INNER JOIN days d
ON ( s."start" < d.dt + INTERVAL '1' DAY
AND s."end" > d.dt )
GROUP BY dt
ORDER BY dt
<强> Results 强>:
| DT | HOURS_WORKED |
|----------------------|----------------------|
| 2017-10-02T00:00:00Z | 2.45 |
| 2017-10-03T00:00:00Z | 3.1333333333333333 |
| 2017-10-04T00:00:00Z | 2.3333333333333335 |
| 2017-10-05T00:00:00Z | 0.9166666666666666 |
| 2017-10-16T00:00:00Z | 2.0166666666666666 |
| 2017-10-17T00:00:00Z | 0.016666666666666666 |
| 2017-10-18T00:00:00Z | 1.1666666666666667 |
| 2017-10-19T00:00:00Z | 2.1 |
| 2017-10-20T00:00:00Z | 1 |
答案 1 :(得分:0)
一种简单的方法是将import React, { Component } from 'react';
import { connect } from 'react-redux';
import BigProfile from './components/bigProfile';
import fetchStudents from './actions/fetch';
import BigButton from './components/bigButton';
import ProfileListContainer from './components/profileListContainer';
export class App extends Component {
constructor(props) {
super(props);
this.state = {
studentName: ''
};
}
pickStudent(array) {
var index = Math.floor(Math.random() * array.length);
var student = array[index];
var studentName = student.name;
this.setState({ studentName: student.name });
this['studentName'] = studentName;
console.log(studentName);
}
componentWillMount() {
this.props.fetchStudents();
}
render() {
const { students } = this.props;
return (
<div className="App">
<BigProfile name={this['studentName']} />
<BigButton
onClick={() =>
this.pickStudent(selectStudentGroup(students, pickColor()))}
/>
<ProfileListContainer />
</div>
);
}
}
const mapStateToProps = store => {
return {
students: store.students
};
};
export default connect(mapStateToProps, { fetchStudents })(App);
合并为1列,将start/end date
合并到其他列,start_hours/end_hours
trunc
列,date
日期并计算{{ 1 {} group by
列,如下所示。
sum
<强>结果:强>
hours
<强> DEMO 强>
答案 2 :(得分:0)
非常感谢你的帮助@ MT0。最后我做到了这一点:
SELECT dt,
NVL(SUM(
LEAST( SIXTY, dt + INTERVAL '1' DAY )
- GREATEST( ZERO, dt )
) * 24, 0.0) AS hours_worked
FROM shitf s
RIGHT JOIN
(SELECT TO_DATE('2017-10-01 00:00:00', 'YYYY/MM/DD HH24:MI:SS')+LEVEL-1 AS dt
FROM DUAL CONNECT BY LEVEL <= TO_CHAR(LAST_DAY(TO_DATE('2017-10-01 00:00:00', 'YYYY/MM/DD HH24:MI:SS')),'DD')) d
ON (s.ZERO < d.dt + INTERVAL '1' DAY
AND s.SIXTY > d.dt )
GROUP dt
ORDER dt
答案 3 :(得分:-1)
SELECT T1.START_DATE,nvl(T1.START_DAY_HOURS,0) + nvl(T2.END_DAY_HOURS,0) TOTAL_HOURS
FROM
(SELECT TRUNC(START) START_DATE,sum(nvl(START_DAY_HOURS,0)) START_DAY_HOURS FROM YOUR_TABLE GROUP BY TRUNC(START)) T1
LEFT JOIN (SELECT TRUNC(END) END_DATE,SUM(nvl(END_DAY_HOURS,0)) END_DAY_HOURS FROM YOUR_TABLE GROUP BY TRUNC(END)) T2
ON T1.START_DATE = T2.END_DATE