Показано с 21 по 33 из 33
Есть ли спецы по MS SQL server
-
24.10.2012, 01:18 #21
- Регистрация
- 01.04.2008
- Пол: Мужской (Male)
- Адрес: Gomel
- Авто: Nissan Primera P11 GT
- Сообщений
- 1,286
мб это? Шардирование aka партиционирование. В реальности геморрой еще тот, и проработка структуры базы требуется серьезная. Проблема в том что секции по каким-то условиям задаются, а эти условия не всегда получается проследить. Мы у себя уже несколько раз поднимали этот вопрос, но как-то все на потом откладывается.
PS: в MS SQL тоже есть такое http://www.sql.ru/articles/mssql/200...dindexes.shtml
-
28.08.2013, 17:12 #22
- Регистрация
- 25.06.2010
- Пол: Мужской (Male)
- Адрес: Гомель
- Авто: ROVER 600
- Сообщений
- 7,036
AlikForever, вот еще загадко. Тока что возникла.
Преамбле:
То же оборудование. Каждый лишний запрос в нем превращается в 20-40 строк кода и время реакции увеличивается в 3 раза. Соответственно, пытаемся свести их к минимуму.
Задача:
Вставить запись, получить ее код, что бы насовать потом этой записи "подчиненных" в другую таблицу. Одним запросом.
На постгре, естественно "SELECT * FROM func(a,b,c,d)", где в func можно повставлять в сотню таблиц сотню записей, и вернуть то что нуна.
В MS - засада. Процедура вызывается EXEC, нужно где-то декларировать переменную, как ее потом вернуть в виде набора из одной записи с одним полем - непонятно.
Пробовал UDF.
CREATE FUNCTION dbo.p_ti_create ( @wpid TINYINT, --- Код завода
@plid TINYINT, --- Код завода (может быть 0)
@liid TINYINT, --- Код линии (может быть 0)
@in_no VARCHAR(15),
@car_no VARCHAR(10),
@prid INT, --- Код товара
@reid INT, --- Код рецепта
@vol FLOAT --- Заданый объем
)
RETURNS @out table (id int)
AS
BEGIN
DECLARE @tid INT;
INSERT INTO tickets (wp_id, in_no, car_no, product_id, recipe_id, volume)
VALUES (@wpid, @in_no, @car_no, @prid, @reid, @vol);
SET @tid = SCOPE_IDENTITY();
INSERT @out (id) VALUES(@tid);
INSERT INTO ticket_events (ticket_id, plant_id, line_id, st)
VALUES (@tid, @plid, @liid, 1);
RETURN
END
Как быть?
-
28.08.2013, 17:40 #23
- Регистрация
- 25.06.2010
- Пол: Мужской (Male)
- Адрес: Гомель
- Авто: ROVER 600
- Сообщений
- 7,036
Подумал, может как-то сформировать строку, содержащую сразу все записи и передать ее на выполнение процедуре? Есть у него какой-нить толковый разборщик строк? Типа strtok
- - - Добавлено - - -
И может знаешь простой способ аналога LIMIT?
-
28.08.2013, 19:59 #24
- Регистрация
- 25.06.2010
- Пол: Мужской (Male)
- Адрес: Гомель
- Авто: ROVER 600
- Сообщений
- 7,036
Подумал, я наверное неверно поступаю. Навязываю свое видение. Короче. Есть структура:
struct p_data
id: int
mix_of_fields: <int, real, time>
end_struct
struct portion
id: int
mix_of_fields: <int, real, time>
data: array [0..15] of p_data
end_struct
struct history
id: int
mix_of_fields: <int, real, time>
portions: array [0..19] of portion
end_struct
т.е. структура "история" имеет несколько подструктур "порции", в каждой порции - некоторое кол-во данных.
Нужно это дело сохранить по соответствующим таблицам.
И есть хитрость. Данная структура может заполняться долго (порядка 10-15 мин), а базу нужно держать как можно актуальнее.
Поэтому, создан "обходчик", который раз в секунду обходит структуру, находит те записи, у которых id = 0, но остальные данные заполнены и в зависимости от того, на каком "подуровне" он находится, формирует SQL на запись данного элемента. Затем присваивает код новой записи полю id и в следующий раз ее пропускает. После того, как все уровни будут заполнены и записаны, миссия считается выполненной.
-
28.08.2013, 23:07 #25
- Регистрация
- 01.04.2008
- Пол: Мужской (Male)
- Адрес: Gomel
- Авто: Nissan Primera P11 GT
- Сообщений
- 1,286
sansa, какие-то странные условия у вас там а каких-нить batch insert-ов не используете? Т.е. надо чтоб вся логика в одной процедуре была?
PS: кстати почему очередь на обновление не сделали, зачем бегать каждый раз по структуре?
- - - Добавлено - - -
Вот нашел прикольный пример. Передают в параметры функции XML, а дальше его парсят.
http://stackoverflow.com/questions/1...ored-procedure
PS: я просто на работе уже года 4 как функций не писал, в базе даже FK уже не встришь у нас. Расскажи попроще что нужно, что-то я до сих пор не понял в чем проблема. По идее если ты передашь в функцию все нужные параметры, то внутри можно сделать будет что угодно.
-
28.08.2013, 23:23 #26
- Регистрация
- 01.04.2008
- Пол: Мужской (Male)
- Адрес: Gomel
- Авто: Nissan Primera P11 GT
- Сообщений
- 1,286
Вот гигантский обзор http://www.sommarskog.se/arrays-in-sql-2005.html
-
28.08.2013, 23:47 #27
- Регистрация
- 25.06.2010
- Пол: Мужской (Male)
- Адрес: Гомель
- Авто: ROVER 600
- Сообщений
- 7,036
Вот код, который в "цикле" читает 10 записей по одному полю из базы данных (на самом деле полей 4, но они на сервере упаковываются в строку, потому распарсить ее быстрее, чем читать по одному).
CASE step OF rbuBDC_CONNECT:
strcpy(ADR(ErrMsg), ADR(''));
codi.enable:= TRUE;
codi.DBCD:= DBCDCurr;
step:= rbuBDC_CONNECT_r;
rbuBDC_CONNECT_r:
codi();
step:= CheckDbConnected(codi.status, step, rbuBDC_CONNECT_DONE, rbuBDC_ERROR);
rbuBDC_CONNECT_DONE:
step:= rbuDB_RD_BU_COMP;
(********************************************************************
* Чтение компонентов бункеров
********************************************************************)
rbuDB_RD_BU_COMP:
rbuDBUBuSQL(ADR(vSQL), PlantID, GLine1.ID);
dbs.enable:= TRUE;
dbs.connectionIdent:= codi.ident;
dbs.pSqlStatement:= ADR(vSQL);
step:= rbuDB_RD_BU_COMP_r;
rbuDB_RD_BU_COMP_r:
dbs();
I:= 1;
step:= CheckDbStatus(dbs.status, step, rbuDB_RD_BU_COMP_FNR, rbuBDC_ERROR);
rbuDB_RD_BU_COMP_FNR: // Получение следующей записи
bunker_id:= 0;
component_id:= 0;
fnr.enable:= TRUE;
fnr.connectionIdent:= codi.ident;
step:= rbuDB_RD_BU_COMP_FNR_r;
rbuDB_RD_BU_COMP_FNR_r:
fnr();
step:= CheckDbStatus(fnr.status, step, rbuDB_RD_BU_COMP_GD, rbuDB_RD_BU_COMP);
rbuDB_RD_BU_COMP_GD: // получение упакованых данных (поле dat)
gd(enable:= TRUE, connectionIdent:= codi.ident,
columnIdx:= 1,
dataType:= DB_SQL_CHAR,
pData:= ADR(s1),
dataSize:= SIZEOF(s1)
);
step:= CheckDbStatus(gd.status, step, rbuDB_RD_BU_COMP_GD_Parse, rbuBDC_ERROR);
rbuDB_RD_BU_COMP_GD_Parse: // рапаковка строки по полям
n:= toktoud(ADR(s1), ADR(bunker_id), DEF_DELIM);
n:= strtok(n, ADR(bun), DEF_DELIM, SIZEOF(bun));
n:= toktoud(n, ADR(component_id), DEF_DELIM);
n:= strtok(n, ADR(bucn), DEF_DELIM, SIZEOF(bun));
step:= rbuDB_RD_BU_COMP_GD_DONE;
rbuDB_RD_BU_COMP_GD_DONE: // Запись считана (если 10, выходим, иначе снова в цикл)
IF IDXValid(bunker_id, BUNKER_COUNT) THEN
BUParams[bunker_id].CoID:= component_id;
BUParams[bunker_id].Name:= bun;
BUParams[bunker_id].CoN:= bucn;
I:= I + 1;
IF (I <= BUNKER_COUNT) THEN
step:= rbuDB_RD_BU_COMP_FNR;
ELSE
step:= rbuDB_RD_TICKET;
END_IF
ELSE
step:= rbuBDC_ERROR;
END_IF
rbuBDC_ERROR:
I:= 0;
ErrMsg:= 'Unknown DB error!';
gem.enable:= TRUE;
gem.connectionIdent:= codi.ident;
gem.pErrorMessage:= ADR(ErrMsg);
gem.errorMessageSize:= SIZEOF(ErrMsg);
step:= rbuBDC_ERROR_r;
rbuBDC_ERROR_r:
gem();
IF I < 20 THEN
step:= CheckDbStatus(gem.status, step, rbuBDC_ERROR_DONE, rbuBDC_ERROR_r);
ELSE
step:= rbuBDC_ERROR_DONE;
END_IF
I:= I + 1;
rbuBDC_ERROR_DONE:
DBError[0]:= TRUE;
IF TEP.Q THEN
step:= rbuBDC_DISCONNECT;
END_IF
rbuBDC_DISCONNECT:
codi.done:= TRUE;
step:= rbuBDC_DISCONNECT_r;
rbuBDC_DISCONNECT_r:
codi();
IF (codi.status = 0) AND (codi.ident = 0) THEN
step:= rbuBDC_CONNECT;
END_IF
END_CASE;
Как ты думаешь, при таком коде еще не созрела мысль воспользоваться все-таки одним запросом? ))
думал, но это подходит для записи всей структуры целиком. А по ТЗ необходимо содержимое БД близкое по времени к структуре. Т.е. для данного случая, нужно ожидать пока вся структура заполнится.
- - - Добавлено - - -
Нужно:
Выполнить один запрос с параметрами, который вставит параметры в указанную таблицу, и вернет ID вставленной записи.
т.е
SELECT id FROM insert_fields_to_table1(@id, @f1, @f2, @f3)
-
29.08.2013, 00:27 #28
- Регистрация
- 01.04.2008
- Пол: Мужской (Male)
- Адрес: Gomel
- Авто: Nissan Primera P11 GT
- Сообщений
- 1,286
Ну, пишешь функцию которая делает insert и возвращает SCOPE_IDENTITY. Почему не подходит?
Вот пример с гугла, по идее работать должен:
CREATE PROCEDURE [dbo].[INS_FlightNewLeg]
@leg1 int,
@leg2 int,
@leg3 int,
@NewLegID int OUTPUT
AS
BEGIN
SET NOCOUNT ON;
INSERT INTO FlightLegs
Values(
@leg1,@leg2,@leg3
)
SELECT @NewLegID = SCOPE_IDENTITY()
END
- - - Добавлено - - -
я думал у тебя записи пачками накапливаются и ты хочешь пачками их записывать (одним селектом).
-
29.08.2013, 00:49 #29
-
29.08.2013, 01:22 #30
- Регистрация
- 01.04.2008
- Пол: Мужской (Male)
- Адрес: Gomel
- Авто: Nissan Primera P11 GT
- Сообщений
- 1,286
ну если клиент SQL, то как-то так
declare @myRes int
exec [dbo].[INS_FlightNewLeg] @leg1 = 1, @leg2 = 2, @leg3 = 3, @NewLegID = @myRes output
А если нет, то все от языка зависит.
если JDBC, то вот так (с гугла своровано, но похоже на правду)
CallableStatement proc = connection.prepareCall("{ ? = call dbo.mySproc() }");
proc.registerOutParameter(1, Types.INTEGER);
proc.execute();
int returnValue = proc.getInt(1);
PS: у тебя какой клиент? я думаю гугл и с ним поможет
- - - Добавлено - - -
Кстати, если у тебя только id возвращается, то лучше сделать так:
Using Return
The last way to get data back from a stored procedure is also the most limiting. It only returns a single numeric value. This is most commonly used to return a status result or error code from a procedure. Consider this procedure:
CREATE PROC dbo.TestReturn (@InValue int)
AS
Return @Invalue
GO
The following script calls the TestReturn stored procedure:
DECLARE @ReturnValue INT
EXEC @ReturnValue = TestReturn 3
SELECT ReturnValue=@ReturnValue
-
29.08.2013, 01:26 #31
- Регистрация
- 01.04.2008
- Пол: Мужской (Male)
- Адрес: Gomel
- Авто: Nissan Primera P11 GT
- Сообщений
- 1,286
и тогда твоя процедурка будет вроде:
CREATE PROCEDURE [dbo].[INS_FlightNewLeg]
@leg1 int,
@leg2 int,
@leg3 int
AS
BEGIN
SET NOCOUNT ON;
INSERT INTO FlightLegs
Values(
@leg1,@leg2,@leg3
)
return SCOPE_IDENTITY()
END
PS: ну и вызов какой-то такой EXEC @ReturnValue = [dbo].[INS_FlightNewLeg] 1,2,3
-
29.08.2013, 13:45 #32
-
27.10.2014, 22:19 #33
- Регистрация
- 25.06.2010
- Пол: Мужской (Male)
- Адрес: Гомель
- Авто: ROVER 600
- Сообщений
- 7,036
Алик, можешь еще помочь? Не нашел на просторах решения, сам в силу незнания пока не могу.
Есть древовидная таблитсо: pt (id:int, parent_id: int, n:varchar(20))
Добавляю в нее поле с новомодной для 2008 фишкой "hierarchyid". В итоге, имеем, pt (id:int, parent_id: int, n:varchar(20), hid:hierarchyid)
Задача. Обновить поле hid в соответствии с id, parent_id. Тригеры на вставку/обновление ослилил с помощью TechNet, все новые данные вставляются и обновляются нормально (если, конечно hid уже заполнен). А вот существующие... Как не получаиццо, второй день. Пример от MS предназначен только для 1 уровня вложения, а выгружать/удалять/загружать обратно данные, и не труъ и невозможно, много таблиц с зависимостями.
Здесь мы обсуждаем
Есть ли спецы по MS SQL server
Похожие темы
-
Ищу, найду, отдам, возьму... Есть работаКому интересно. Работа с компьютерами: настройка, подключение. Заправка картриджей, ремонт принтеров, настройка сети... Гос контора. Оплата точно не скажу, от 1,5-3млн. Работа в 2-ве смены. Очень срочно. Ищу себе сменщика. Собеседование с...
-
Ищу, найду, отдам, возьму... Есть ли у кого фреза?САБЖ, возьму поюзать на пару дней за пиво-соки-шоколадки
-
Ищу, найду, отдам, возьму... есть запаска на 13колесо (запаска) с диском на фольксваген . бескамерная Goodyear, 175/70/13, б/у, 1 шт.75% износа ,цена 30000 руб., т. (8-044)710-97-28, Вел P.S Рассмотрю любые предложения.
-
Обслуживание и эксплуатация авто СПИСОК Дизель сервисы, и просто спецы по дизелямРебята скиньте кто знает какие.
-
Автосервис Гомеля Где есть спецы по радиаторам?:)На днях сниму радиатор, нужно выявить откуда потек, кому завезти на диагностику? Спасибо.