Вы используете блок try-исключения для обработки чтения пустых записей, но затем продолжаете пытаться обрабатывать их. Этот код обработки также должен находиться внутри блока try
:
# Calculate the min and max values in the current interval based on the SECOND value (force, not distance)
# This is what the lambda function is for
try:
minimum = min(current_interval, key=lambda t: int(t[1]))
maximum = max(current_interval, key=lambda t: int(t[1]))
# This was originally outside the "try" block
# Write the values for the current interval
datawriter.writerow([interval_count, '', minimum[1], minimum[0], '', maximum[1], maximum[0]])
interval_count += 1 # Update count
except ValueError:
pass # Code was throwing errors for blank entries, this just skips them
Я использовал бы эту хранимую процедуру для генерации интервалов, в которых Вы нуждаетесь во временную таблицу, названную time_intervals, затем ПРИСОЕДИНЯЕТЕСЬ и агрегировали свою таблицу данных с временным файлом таблица time_intervals .
процедура может генерировать интервалы всех различных типов, которые Вы видите указанный в ней:
call make_intervals('2009-01-01 00:00:00','2009-01-10 00:00:00',1,'DAY')
.
select * from time_intervals
.
interval_start interval_end
------------------- -------------------
2009-01-01 00:00:00 2009-01-01 23:59:59
2009-01-02 00:00:00 2009-01-02 23:59:59
2009-01-03 00:00:00 2009-01-03 23:59:59
2009-01-04 00:00:00 2009-01-04 23:59:59
2009-01-05 00:00:00 2009-01-05 23:59:59
2009-01-06 00:00:00 2009-01-06 23:59:59
2009-01-07 00:00:00 2009-01-07 23:59:59
2009-01-08 00:00:00 2009-01-08 23:59:59
2009-01-09 00:00:00 2009-01-09 23:59:59
.
call make_intervals('2009-01-01 00:00:00','2009-01-01 02:00:00',10,'MINUTE')
.
select * from time_intervals
.
interval_start interval_end
------------------- -------------------
2009-01-01 00:00:00 2009-01-01 00:09:59
2009-01-01 00:10:00 2009-01-01 00:19:59
2009-01-01 00:20:00 2009-01-01 00:29:59
2009-01-01 00:30:00 2009-01-01 00:39:59
2009-01-01 00:40:00 2009-01-01 00:49:59
2009-01-01 00:50:00 2009-01-01 00:59:59
2009-01-01 01:00:00 2009-01-01 01:09:59
2009-01-01 01:10:00 2009-01-01 01:19:59
2009-01-01 01:20:00 2009-01-01 01:29:59
2009-01-01 01:30:00 2009-01-01 01:39:59
2009-01-01 01:40:00 2009-01-01 01:49:59
2009-01-01 01:50:00 2009-01-01 01:59:59
.
I specified an interval_start and interval_end so you can aggregate the
data timestamps with a "between interval_start and interval_end" type of JOIN.
.
Code for the proc:
.
-- drop procedure make_intervals
.
CREATE PROCEDURE make_intervals(startdate timestamp, enddate timestamp, intval integer, unitval varchar(10))
BEGIN
-- *************************************************************************
-- Procedure: make_intervals()
-- Author: Ron Savage
-- Date: 02/03/2009
--
-- Description:
-- This procedure creates a temporary table named time_intervals with the
-- interval_start and interval_end fields specifed from the startdate and
-- enddate arguments, at intervals of intval (unitval) size.
-- *************************************************************************
declare thisDate timestamp;
declare nextDate timestamp;
set thisDate = startdate;
-- *************************************************************************
-- Drop / create the temp table
-- *************************************************************************
drop temporary table if exists time_intervals;
create temporary table if not exists time_intervals
(
interval_start timestamp,
interval_end timestamp
);
-- *************************************************************************
-- Loop through the startdate adding each intval interval until enddate
-- *************************************************************************
repeat
select
case unitval
when 'MICROSECOND' then timestampadd(MICROSECOND, intval, thisDate)
when 'SECOND' then timestampadd(SECOND, intval, thisDate)
when 'MINUTE' then timestampadd(MINUTE, intval, thisDate)
when 'HOUR' then timestampadd(HOUR, intval, thisDate)
when 'DAY' then timestampadd(DAY, intval, thisDate)
when 'WEEK' then timestampadd(WEEK, intval, thisDate)
when 'MONTH' then timestampadd(MONTH, intval, thisDate)
when 'QUARTER' then timestampadd(QUARTER, intval, thisDate)
when 'YEAR' then timestampadd(YEAR, intval, thisDate)
end into nextDate;
insert into time_intervals select thisDate, timestampadd(MICROSECOND, -1, nextDate);
set thisDate = nextDate;
until thisDate >= enddate
end repeat;
END;
Подобный сценарий данных в качестве примера у основания это сообщение , где я создал подобную функцию для SQL Server.
Создайте хранимую процедуру, которая берет два параметра a_begin и a_end. Составьте временную таблицу в нем, назвал t, объявите переменную d, присвойте a_begin d и работайте WHILE
цикл INSERT
луг d в t и вызов ADDDATE
функция для постепенного увеличения значения d. Наконец SELECT * FROM t
.
Обычно можно было бы использовать вспомогательный глагол, числа представляют Вас в виде таблицы, обычно имеют в наличии для просто этой цели с некоторой вариацией на это:
SELECT *
FROM (
SELECT DATEADD(d, number - 1, '2009-01-01') AS dt
FROM Numbers
WHERE number BETWEEN 1 AND DATEDIFF(d, '2009-01-01', '2009-01-13') + 1
) AS DateRange
LEFT JOIN YourStuff
ON DateRange.dt = YourStuff.DateColumn
я видел изменения с табличными функциями, и т.д.
можно также сохранить постоянный список дат. У нас есть это в нашем хранилище данных, а также списке времени суток.
Одалживая идею от этот ответ, можно настроить таблицу с 0 до 9 и использование что генерировать список дат.
CREATE TABLE num (i int);
INSERT INTO num (i) VALUES (0), (1), (2), (3), (4), (5), (6), (7), (8), (9);
select adddate('2009-01-01', numlist.id) as `date` from
(SELECT n1.i + n10.i*10 + n100.i*100 AS id
FROM num n1 cross join num as n10 cross join num as n100) as numlist
where adddate('2009-01-01', numlist.id) <= '2009-01-13';
Это позволит Вам генерировать список до 1 000 дат. Если необходимо пойти более крупные, можно добавить другое перекрестное объединение к внутреннему запросу.
Можно использовать пользовательские переменные MySQL как это:
SET @num = -1;
SELECT DATE_ADD( '2009-01-01', interval @num := @num+1 day) AS date_sequence,
your_table.* FROM your_table
WHERE your_table.other_column IS NOT NULL
HAVING DATE_ADD('2009-01-01', interval @num day) <= '2009-01-13'
@num-1, потому что Вы добавляете к нему в первый раз, когда Вы используете его. Кроме того, Вы не можете использовать "НАЛИЧИЕ date_sequence", потому что это делает инкремент пользовательской переменной дважды для каждой строки.
У нас была подобная проблема с отчетами BIRT, в которых мы хотели сообщить в те дни, которые не имели никаких данных. С тех пор не было никаких записей для тех дат, самое легкое решение для нас состояло в том, чтобы составить простую таблицу, которая сохранила все даты, и используйте это, чтобы заставить диапазоны или соединение получать нулевые значения для той даты.
у Нас есть задание, которое работает каждый месяц, чтобы гарантировать, что таблица заполняется 5 лет в будущее. Таблица составлена таким образом:
create table all_dates (
dt date primary key
);
Несомненно существуют волшебные хитрые способы сделать это с другим DBMS, но мы всегда выбираем простое решение. Требования устройства хранения данных для таблицы минимальны, и она делает запросы настолько более простыми и портативными. Этот вид решения почти всегда лучше с точки зрения производительности, так как это не требует вычислений на строку на данных.
другая опция (и мы использовали это прежде) состоит в том, чтобы гарантировать, что существует запись в таблице для каждой даты. Мы периодически развертывали таблицу и добавляли нулевые записи для дат и/или времена, которые не существовали. Это не может быть опцией в Вашем случае, это зависит от хранивших данных.
, Если Вы действительно думаете, что это - стычка для хранения all_dates
таблица заполненным, хранимая процедура является способом пойти, который возвратит набор данных, содержащий те даты. Это почти наверняка будет медленнее, так как необходимо вычислить диапазон каждый раз, когда вместо этого называют того, чтобы просто вытянуть предварительные расчетные данные от таблицы.
, Но, честно говоря, Вы могли заполнить таблицу в течение 1 000 лет без любых серьезных проблем хранения данных - 365 000 16 байтов (например), даты плюс индекс, копирующий дату плюс 20% наверху для безопасности, я примерно оценю приблизительно в 14M [365,000 * 16 * 2 * 1.2 = 14 016 000 байтов]), крохотная таблица в схеме вещей.
Я бы использовал что-то подобное:
DECLARE @DATEFROM AS DATETIME
DECLARE @DATETO AS DATETIME
DECLARE @HOLDER TABLE(DATE DATETIME)
SET @DATEFROM = '2010-08-10'
SET @DATETO = '2010-09-11'
INSERT INTO
@HOLDER
(DATE)
VALUES
(@DATEFROM)
WHILE @DATEFROM < @DATETO
BEGIN
SELECT @DATEFROM = DATEADD(D, 1, @DATEFROM)
INSERT
INTO
@HOLDER
(DATE)
VALUES
(@DATEFROM)
END
SELECT
DATE
FROM
@HOLDER
Затем в таблице переменных @HOLDER
хранятся все даты, увеличенные на день между этими двумя датами, которые можно соединять по своему усмотрению.