powered by simpleCommunicator - 2.0.59     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Microsoft SQL Server [игнор отключен] [закрыт для гостей] / Типы данных datetime
9 сообщений из 9, страница 1 из 1
Типы данных datetime
    #32008696
SOVA
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Объясняю ситуацию:
есть таблица HistoryTable которая хранит историю состояния объекта. Поля : DateBegin (тип smalldatetime - дата начала срока действия состояния объекта), DateEnd (тип smalldatetime - дата окончания срока действия состояния объекта), S - int (собственно состояние объекта, неважно что оно отражает) Так вот... данная таблица истории позволяет узнать состояние объекта на заданную дату! Достаточно выполнить запрос SELECT S FROM HistoryTable WHERE @D BETWEEN DateBegin AND DateEnd где @D - заданная дата!
Логически все просто, но поля типа smalldatetime хранят еще и время которое мне совершенно не нужно! Мне необходима точность действия состояния объекта до суток, а не до секунд. Соответственно когда я задаю в качестве параметра @D только дату в него еще подставляется текущее время и результаты запроса искажаются! Еще ко всему в таблицу HistoryTable так-же заносится время! Как и когда мне от этого избавится? Во время вставки данных в HistoryTable приводить все поля smalldatetime к единому времени (не дате)? или делать это во время выполнения запроса (приведенный запрос в хранимой процедуре) ... или есть другой способ?

Подсказывайте!
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008701
maximF
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Может быть так:
в триггере
update inserted set dateBegin = cast( cast( dateBegin as int) as DateTime )
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008703
Фотография Garya
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Я тоже ковыряю аналогичные задачки.
Я веду две истории. Одна по учетному времени, вторая по календарному. По учетному времени действительно нет необходимости хранить секунды, минуты и часы. Отсюда же следует, что период действия записей на учетном времени удобно задавать полями типа smalldatetime, а не datetime - это сократит размер записии увеличит скорость выборки по индексу. Откусить лишнее можно в триггере на insert/update (а можно и не откусывать, если заведомо известно, что клиентское приложение никогда не вернет дату вместе со временем).
Кроме того, я пришел к выводу, что задавать начало и конец срока действия в одной записи нерационально с точки зрения конфликтности репликации. Я храню ОДНО поле для указания периода дейтсвия данной редакции на оси учетного времени - дату окончания действия редакции. Если Null, то оно равно бесконечности. Пример. Две записи имеют разные периоды окончания их действия, и это редакции одной записи справочника. Они разбивают ось учетного времени на три отрезка - ]-бесконечность, срок окончания действия первой записи] - на этом отрезке действует первая запись; ]срок окончания действия первой записи, срок окончания действия второй запис записи] - на этом отрезке действует вторая запись; ]срок окончания действия второй записи, плюс бесконечность[ - на этом отрезке не действует ни одна редакция записи.
Для журнализации всех операций над записями вводится поле календарное время создания редакции записи (а с ним еще ID пользователя, создавшего редкацию, имя компьютера, с которого она создана). Это поле на клиенте вообще недоступно, но имеет значение по умолчанию Getdate(). Назначение понятно.
Еще одно поле (bit) - флаг логического удаления. Любая модификация записей с помощью instead-триггеров превращается в добавление новой редакции записи. Прежние редакции не удаляются, и по ним не производится update. Актуальные записи отфильтровываются из истории с помощью VIEW. Модификация записи - это добавление новой редакции записи с более поздней календарной датой создания. Именно по календарной дате создания определяется актуальность записи. Удаление записи приводит к моявлению новой редакции записи с установленным флагом логического удаления. При настроке Merge-репликации конфликты отсутствуют как класс. В то же время в самой таблице лежит журнал модификации, в котором можно подглядеть, что и когда шевелил (плюс к тому еще и на каком из удаленных узлов корпоративной сети).
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008714
SOVA
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
To maximf: 1 нельзя апдейтить таблицы inserted и deleted! Но... ты очень помог! данная конструкция (dateBegin = cast( cast( dateBegin as int) as DateTime ) действительно обрубает время! А это мне и надо было! Поклон великий!

To Garya:
Да... возможны конфликты при репликации! Согласен! Но... 1 - у меня это история редкоизменяющихся параметров объекта! И я не очень уверен что и ваша организация истории оптимальна! Я всетаки настаиваю на своей! ) потому как помучался в свое время с такой как у вас. не думаю что эллементарный запрос на выборку значения на заданную дату будет очень простым! Давайте обсудим! ) мне это интересно...
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008715
Фотография SergSuper
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
2 maximf

create table #d(dateBegin datetime)
insert #d select '20010101 10:00'
insert #d select '20010101 20:00'

update #d set dateBegin = cast( cast( dateBegin as int) as DateTime )

select * from #d

Вообщем не надо такое предлагать. Можно написать так:

update #d set dateBegin = cast( cast( dateBegin-0.5 as int) as DateTime )

Но тоже как-то нехорошо выглядит
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008720
Genady
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Можно еще так

update YourTable set dateBegin = convert(datetime, convert(char(, OperationStop, 1))
Не пробовал но може пройти и так:
update YourTable set dateBegin = convert(char(, OperationStop, 1)

Третий параметр (единица) указывает на формат даты, какие они бывают см в BOL Cast and Convert, можно такой апдейтик засунуть и в триггер, а можно и самому так писать.
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008721
Genady
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Там где рожица выскочила нужно ставить восмерку со скобкой
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008724
Фотография Garya
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Да я-то не настаиваю... Не нравится - не используй. Это просто в порядке обмена опытом.
Могу привести пример запроса, если интересно. Расписывать струтктуру всех участвующих в запросах таблиц слишком долго, но по названиям многое можно понять. Если есть желание позаниматься кодокопательством, то привожу ниже тексты реально работающих запросов.

Запрос, возвращающий последние на оси календарного времени модификации записи справочника единиц измерений (в том числе помеченные как логически удаленные):
CREATE VIEW dbo.vwsprEdIzm_LastsAll with VIEW_METADATA
AS
SELECT MZ.RecID, MZ.Name, MZ.EnableBeforeAccountDate, MZ.Deleted, MZ.PeriodID, MZ.SprID, MZ.UserID, MZ.CalendCreationTime, MZ.FromStation
FROM dbo.sprEdIzm MZ INNER JOIN
(SELECT PeriodID, SprID, MAX(CalendCreationTime) AS LastCalendCreationTime
FROM dbo.sprEdIzm
GROUP BY SprID, PeriodID) SubZ ON MZ.PeriodID = SubZ.PeriodID AND MZ.SprID = SubZ.SprID AND
MZ.CalendCreationTime = SubZ.LastCalendCreationTime CROSS JOIN
dbo.mt_X_UsersAndSpravs X
WHERE (X.UserID = dbo.CurrentUserID()) AND (X.SpravID = '{FE57C16C-E845-4BBD-874E-94975C257FE7}') AND (X.CalcPermRead = 1)

Запрос, возвращающий актуальные на заданную учетную дату записи либо вместе с логически удаленными, либо без них. На какую учетную дату, а также с удаленными или без них, указывается в таблице mt_X_UsersAndSpravs1:

CREATE VIEW dbo.vwsprEdIzm_MainView with VIEW_METADATA
AS
SELECT A1.RecID, A1.PeriodID, A1.SprID, A1.Name, A1.EnableBeforeAccountDate, A1.CalendCreationTime, A1.Deleted
FROM dbo.vwsprEdIzm_LastsAll A1,(SELECT A.SprID, MIN(A.EnableBeforeAccountDate) AS BeforeDate
FROM vwsprEdIzm_LastsAll A, mt_X_UsersAndSpravs1 X1, mtUserSingleParameters P
WHERE X1.UserID = P.UserID AND P.UserID = dbo.CurrentUserID() AND X1.SpravID = 'FE57C16C-E845-4BBD-874E-94975C257FE7' AND
(A.Deleted = X1.ShowDeleted OR
X1.ShowDeleted IS NULL) AND (A.EnableBeforeAccountDate >= P.AccountCurrentPoint OR
A.EnableBeforeAccountDate IS NULL)
GROUP BY A.SprID) B1
WHERE A1.SprID = B1.SprID AND ISNULL(A1.EnableBeforeAccountDate, CONVERT(datetime, '05 may 2000 13:13:13', 113)) = ISNULL(B1.BeforeDate, CONVERT(datetime, '05 may 2000 13:13:13', 113))

Запрос, возвращающий для одной записи справочника, все действующие редакции записи на разных периодах учетного времени (через этот же VIEW производится добавление новых редакций для новых отрезков учетного времени):
CREATE VIEW dbo.vwsprEdIzm_ViewByPeriods with VIEW_METADATA
AS
SELECT A.RecID, A.PeriodID, A.SprID, A.Name, A.EnableBeforeAccountDate, A.CalendCreationTime, A.Deleted
FROM dbo.vwsprEdIzm_LastsAll A INNER JOIN
dbo.mt_X_UsersAndSpravs1 X1 ON A.SprID = X1.CurrentSprID INNER JOIN
dbo.mt_X_UsersAndSpravs X ON X.UserID = X1.UserID AND X.SpravID = X1.SpravID
WHERE (X1.UserID = dbo.CurrentUserID()) AND (X1.SpravID = 'FE57C16C-E845-4BBD-874E-94975C257FE7') AND (X1.ShowDeleted = A.Deleted OR
X1.ShowDeleted IS NULL) AND (X.CalcPermShowMultiPeriods = 1)

Запрос, который для одной выбранной на оси учетного времени редакции записи возвращает историю ее модификации (журнал всех действий над записью) на оси календарного времени:
CREATE VIEW dbo.vwsprEdIzm_ViewPeriodHistory
AS
SELECT TOP 100 PERCENT A.RecID, A.PeriodID, A.SprID, A.Name, U.UserOrRoleName, N.RemoteNodeName, A.CalendCreationTime, A.FromStation,
A.EnableBeforeAccountDate, A.Deleted
FROM dbo.mtRemoteNodes N INNER JOIN
dbo.mtUsersAndRoles U ON N.RemoteNodeID = U.RemoteNodeID INNER JOIN
dbo.sprEdIzm A INNER JOIN
dbo.mt_X_UsersAndSpravs1 X1 ON A.SprID = X1.CurrentSprID AND A.PeriodID = X1.CurrentPeriodID ON U.UserOrRoleID = A.UserID INNER JOIN
dbo.mt_X_UsersAndSpravs X ON X.UserID = X1.UserID AND X.SpravID = X1.SpravID
WHERE (X1.UserID = dbo.CurrentUserID()) AND (X1.SpravID = 'FE57C16C-E845-4BBD-874E-94975C257FE7') AND (X1.ShowDeleted = A.Deleted OR
X1.ShowDeleted IS NULL) AND (X.CalcPermShowHistory = 1)
ORDER BY A.CalendCreationTime
...
Рейтинг: 0 / 0
Типы данных datetime
    #32008738
Fompro
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SELECT CAST(CONVERT(char( 8 ),DateBegin,112) AS int)
Тот же int, только гораздо наглядней.
EXEC sp_addtype 'NDate', 'int', 'null'
GO
+ соответствующий Bind
Да, у нас, например, бывает нужно впихнуть в него 13-й,... (далее везде) месяц.
...
Рейтинг: 0 / 0
9 сообщений из 9, страница 1 из 1
Форумы / Microsoft SQL Server [игнор отключен] [закрыт для гостей] / Типы данных datetime
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]