I am trying to write a query that fetch the latest stats of shift working at a factory but myquery becomes so complex that it took almost 12 seconds to execute in mysql workbench.Any suggestions to optimize my query ?
SELECT c_time,
shift
INTO @c_time,
@shift
FROM roll_header_view
WHERE id = 'id';
SELECT f.*,
employee.name as employee_name,
employee.employee_code as employee_code
FROM roll_header_view f
LEFT OUTER JOIN employee_view employee
ON employee.id = f.employee_id
WHERE c_time <= @c_time
AND c_time >
(SELECT IFNULL(max(c_time), 0)
FROM roll_header_view
WHERE shift != @shift
AND c_time <= @c_time);
'CREATE TABLE `employee` (
`id` bigint(20) NOT NULL DEFAULT ''0'',
`mac_id` int(11) NOT NULL DEFAULT ''100'',
`c_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`u_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`c_by` varchar(100) NOT NULL DEFAULT ''100'',
`u_by` varchar(100) NOT NULL DEFAULT ''100'',
`isactive` varchar(1) NOT NULL DEFAULT ''Y'',
`employee_code` varchar(100) NOT NULL DEFAULT '''',
`name` varchar(100) NOT NULL DEFAULT '''',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1'
'CREATE TABLE `roll_header` (
`id` bigint(20) NOT NULL DEFAULT ''0'',
`mac_id` int(11) NOT NULL DEFAULT ''100'',
`c_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`u_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`c_by` varchar(100) NOT NULL DEFAULT ''100'',
`u_by` varchar(100) NOT NULL DEFAULT ''100'',
`isactive` varchar(1) NOT NULL DEFAULT ''Y'',
`roll_no` bigint(20) NOT NULL DEFAULT ''0'',
`actual_id` bigint(20) NOT NULL DEFAULT ''0'',
`req_cuttable_width` float NOT NULL DEFAULT ''0'',
`act_cuttable_width` float NOT NULL DEFAULT ''0'',
`color` varchar(100) NOT NULL DEFAULT '''',
`contract_no` varchar(100) NOT NULL DEFAULT '''',
`construction` varchar(100) NOT NULL DEFAULT '''',
`finish` varchar(100) NOT NULL DEFAULT '''',
`meter_yard_length` float NOT NULL DEFAULT ''0'',
`meter` float NOT NULL DEFAULT ''0'',
`yard` float NOT NULL DEFAULT ''0'',
`is_meter_yard` varchar(1) NOT NULL DEFAULT ''Y'',
`total_l_point` int(11) NOT NULL DEFAULT ''0'',
`penalty_point` float NOT NULL DEFAULT ''0'',
`trolly_no` varchar(100) NOT NULL DEFAULT '''',
`description` varchar(1000) NOT NULL DEFAULT '''',
`shift` varchar(100) NOT NULL DEFAULT '''',
`shift_end` varchar(1) NOT NULL DEFAULT ''0'',
`shift_start` varchar(1) NOT NULL DEFAULT ''0'',
`quality` varchar(100) NOT NULL DEFAULT ''A'',
`employee_id` bigint(20) NOT NULL DEFAULT ''1'',
PRIMARY KEY (`id`),
KEY `fk_roll_header_employee_id` (`employee_id`),
CONSTRAINT `roll_header_ibfk_1` FOREIGN KEY (`employee_id`) REFERENCES `employee` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1'
I have shared all the relevant data for this query ie table structure ER diagram Explain etc kindly help me optimizing this query in a better and performance oriented way Explain plan
I've tried to figure out what your query is supposed to do - I'm sure there's a better way to write it, but it makes very little sense to me.
I've converted it to a SQL Fiddle, here: http://sqlfiddle.com/#!9/5435e2/6
The problem is that your subquery
(SELECT IFNULL(max(c_time), 0)
FROM roll_header_view
WHERE shift != @shift
AND c_time <= @c_time);
is being executed for every row it compares, and cannot use an index. If you re-write the query as follows, that problem goes away.
SELECT c_time,
shift
INTO @c_time,
@shift
FROM roll_header
WHERE id = 'id';
SELECT @max_time = IFNULL(max(c_time), 0)
FROM roll_header
WHERE shift != @shift
AND c_time <= @c_time;
SELECT f.*,
employee.name as employee_name,
employee.employee_code as employee_code
FROM roll_header f
LEFT OUTER JOIN employee employee
ON employee.id = f.employee_id
WHERE f.c_time <= @c_time
AND f.c_time >
@max_time;
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.