Имя: Пароль:
1C
1С v8
Выборка не первых записей из ТЗ
,
0 Cоляпсус
 
08.12.17
10:40
Здравствуйте, снова вынужден спросить совета
Есть обработка, которая делает корректировки регистров,создавая документы корректировки, по просьбе заказчика в целях оптимизации работы этой обработки, чтобы не нагружать систему, необходимо создавать документы не более (предположим) 200 записей. Предположим, что получается документ с 230 записями. Тем самым необходимо бить 200 записей создавать документ и создавать новый документ с оставшимися 30-ю записями. обработка делает различные действия и создаёт необходимую ТЗ из которой потом создаются док. ТЗ соответственно содержит 230 записей.Как отобрать первые 200 с внешней &ТЗ запросом, это понятно, но вот в чём встал вопрос как отобрать остальные 30 этой же ТЗ и создать новый документ. Не могу понять как бы мне задать условия отбора, если в принципе наверное я могу отобраться по индексу или как-то ещё. Других полей на которые можно было бы опереться не вижу
Заранее благодарен
1 Cоляпсус
 
08.12.17
10:44
В конструкторе есть поле индекс, но честно не знаю как оно работает
2 Cоляпсус
 
08.12.17
10:45
*вкладка индекс
3 hhhh
 
08.12.17
10:51
(1) ну типа

ГДЕ
   НомерСтроки > 200
4 Cоляпсус
 
08.12.17
11:07
(3) А увидит он НомерСтроки или ругнётся на него, явного же такого поля нет. И как я понял это надо делать вторым запросом? Сначала запрос до 200 создать документ, потом снова туда же запрос >200 создать документ? Или всё можно описать в рамках одного запроса?
5 hhhh
 
08.12.17
11:29
(4) ну есть же такое поле у тз
6 Ц_У
 
08.12.17
11:31
(4) выбрать первые 200 отсортировать в обратную сторону, вбрать первые 200 :)
7 Ц_У
 
08.12.17
11:34
выбрать строка из тз где строка не в (выбрать первые 200 из тз)
8 Рэйв
 
08.12.17
11:34
(0)А зачем тебе именно запросом?ВСе равно же строки потом перебирать чтобы движения делать.
Выбирай первые 200 и удаляй их. Потом оставшиеся 30
9 Cоляпсус
 
08.12.17
11:34
(5) у ТЗ есть вот такие поля:
http://pastenow.ru/803ffb5eb768631f5feade5bbf75a608
есть конечно поле индекс, но как в запросе к нему обратиться? А других полей к чему прицепиться не вижу((
10 Lama12
 
08.12.17
11:37
(0) Посмотри как расчет себестоимости в УПП работает. Там это реализовано.
11 Cоляпсус
 
08.12.17
11:39
(8) Ну запросом же типа оптимизированей))
Можно и не запросом, но вот думаю, а можно ли это с запросом реализовать?
12 Cоляпсус
 
08.12.17
11:40
(10) Нет УПП к сожалению
13 Рэйв
 
08.12.17
11:43
(11)Любой инструмент нужно применять с умом.
Тебе вообще делить ТЗ необязательно.Поставь счетчик и перебирай ее.
Как только счетчик=200 записывай документ с движениями и создавай новый
14 Cоляпсус
 
08.12.17
11:45
(8) Ну да можно конечно реализовать это через Для Индекс= сначала 200, создать док, потом Для Индекс = от 200 до граница, создать док. Хотел малой кровью обойтись (через запрос), но не придумал как отобрать записи после 200-тых.... а жаль)
15 Рэйв
 
08.12.17
11:46
(14)легко реализуется как в (13), только еще счетчик надо обнулять
16 Рэйв
 
08.12.17
11:47
или
Если Счетчик%200=0 Тогда...

:-)
17 Ц_У
 
08.12.17
11:47
(14) а (7) тебе чем не подходит?
18 Cоляпсус
 
08.12.17
11:50
(16) уж не знаю корректно ли это в рамках соблюдения правил этики написания кода ,сначала запросом выбрать, а второй раз через цикл и как это влияет на производительность.
а через обнуление счётчика конечно попробую. Спасибо за совет. Только подумаю как это пишется ))
19 Cоляпсус
 
08.12.17
11:51
(17) Не совсем понял как это кодом реализовать, "выбрать не" пробовал с самого начала, синтаксическая ошибка говорит
20 Ц_У
 
08.12.17
11:53
(19) ВЫБРАТЬ
    ТЗ.НомерСтроки КАК НомерСтроки
ИЗ
    &ТЗ КАК ТЗ
ГДЕ
    НЕ ТЗ.НомерСтроки В
                (ВЫБРАТЬ ПЕРВЫЕ 200
                    ТЗ.НомерСтроки
                ИЗ
                    &ТЗ КАК ТЗ)
21 Табуретко
 
08.12.17
11:55
(20) угу а как у него запрос на 430 строк сработает, тогда что?
22 Ц_У
 
08.12.17
11:56
(21) рекурсия
23 Табуретко
 
08.12.17
11:56
(0) делайте как в (13) и не изобретайте лесепеды
24 Ц_У
 
08.12.17
11:58
Порция = 200;
КоличествоПорций = Цел(ТЗ.Количество()/Порция);
И запрос в цикле, ну а что делать, раз надо :)
25 Cоляпсус
 
08.12.17
12:03
(23) Да с учётом что записей может быть разное количество, хотя если брать реальный запрос заказчика, что записей нужно 5000 и делать новый док, вряд ли записей случится (во всяком случае на той базе), например 13000 записей, но полностью с Вами согласен, этот вариант надо предусмотреть и сделать с обнулением счётчика...++
26 Рэйв
 
08.12.17
12:04
(18)>>Только подумаю как это пишется ))

//-------
Что там думать то?:-)
Док=Документы.Твой.СоздатьДокумент();
Сч-0;
Для Каждого Стр из ТЗ Цикл
    //добавляешь движение по Стр
    Если Сч=200 Тогда
        Док.Записать(РежимЗаписиДокумента.Проведение);
        Сч=0
        Док=Документы.Твой.СоздатьДокумент();
    КонецЕсли;
Конеццикла;
Если Сч>0 Тогда
    Док.Записать(РежимЗаписиДокумента.Проведение);
КонецЕсли;
27 Рэйв
 
08.12.17
12:05
*Сч-0; -> Сч=0;
28 catena
 
08.12.17
12:06
(26)Еще счетчик увеличить внутри цикла.
29 Рэйв
 
08.12.17
12:06
+еще забыл:-)

в цикле
Сч=Сч+1;
30 Рэйв
 
08.12.17
12:07
(28)Да, точно:-)
31 Ц_У
 
08.12.17
12:08
(26) (28) и руки вырвать :)
32 Рэйв
 
08.12.17
12:09
(31)За что это?
А то запросом будет оптимальнее,ага...
33 Ц_У
 
08.12.17
12:10
(32) 200 раз перепроводить документ - вон из профессии
34 Рэйв
 
08.12.17
12:11
(33)С хрена ли 200 раз? Внимательно прочитай код прежде чем вонкать:-)
35 Табуретко
 
08.12.17
12:12
и где он 200 раз проводит?
36 Ц_У
 
08.12.17
12:12
(34) уговорил :) пустой документ на 200
37 Табуретко
 
08.12.17
12:12
руки тока подкорректировать чтоб код полностью сразу писал, без правки...
38 Рэйв
 
08.12.17
12:14
(36)Еще раз внимательно прочитай последние 3 строки:-)
39 catena
 
08.12.17
12:15
Так руки или глаза?)))
40 Рэйв
 
08.12.17
12:15
(37)Много вас тут корректировщиков:-)
Сами так же все пишите.Так что нечего тут:-)
41 Табуретко
 
08.12.17
12:17
(39) одному руки, другому глаза...
42 Рэйв
 
08.12.17
12:18
(41)а тебе губу..:-))
43 Табуретко
 
08.12.17
12:21
(42)???
44 Рэйв
 
08.12.17
12:22
(43)....закатать обратно:-)
45 3achem
 
08.12.17
12:24
(25) Делаешь нумерацию в запросе (наростающим итогом), потом выводишь по диапозонам.
Про сч = сч + 1 забудь как про страшный сон
46 Cоляпсус
 
08.12.17
12:33
Запрос = Новый Запрос;
    Запрос.Текст =
        "ВЫБРАТЬ
        |    МояТЗ.ВидДвижения КАК ВидДвижения,
        |    МояТЗ.ИнвентарныйНомер КАК ИнвентарныйНомер,
        |    МояТЗ.Количество,
        |    МояТЗ.Организация,
        |    МояТЗ.ОсновноеСредство,
        |    МояТЗ.Подразделение,
        |    МояТЗ.Стоимость,
        |    МояТЗ.ЦМО,
        |    МояТЗ.ЭтоСписание
        |ПОМЕСТИТЬ ВТ
        |ИЗ
        |    &МояТЗ КАК МояТЗ
        |ГДЕ
        |    НЕ МояТЗ.НомерСтроки В
        |                (ВЫБРАТЬ ПЕРВЫЕ 200
        |                    МояТЗ.НомерСтроки
        |                ИЗ
        |                    &МояТЗ КАК ТЗ)
        |;
        |
        |////////////////////////////////////////////////////////////////////////////////
        |ВЫБРАТЬ
        |    ВТ.ВидДвижения,
        |    ВТ.ИнвентарныйНомер,
        |    ВТ.Количество,
        |    ВТ.Организация,
        |    ВТ.ОсновноеСредство,
        |    ВТ.Подразделение,
        |    ВТ.Стоимость,
        |    ВТ.ЦМО,
        |    ВТ.ЭтоСписание
        |ИЗ
        |    ВТ КАК ВТ";
    
    Запрос.Параметры.Вставить("МояТЗ", МояТЗ1);
    ТЗ30 = Запрос.Выполнить().Выгрузить();
    
    СоздатьДокументКорректировки("СтоимостьОбъектовОС", ТЗ30);
47 Cоляпсус
 
08.12.17
12:33
Ругнулся,что данные можно передать только во временную таблицу, наверное это где условия я ошибся?
48 Рэйв
 
08.12.17
12:37
"Мыши пищали, кололись, но продолжали есть кактус."(С)
49 Ц_У
 
08.12.17
12:37
(47) сначала все в ВТ потом уже обрабатывай
50 Ц_У
 
08.12.17
12:38
(48) циклом любой сможет, а ты запросом дерни :)
51 Cоляпсус
 
08.12.17
12:39
ааа, сейчас поправлю)
52 Рэйв
 
08.12.17
12:40
(50)Только один вопрос - Зачем?:-)
53 Cоляпсус
 
08.12.17
12:45
НомераСтроки то нет же, он и не хочет
54 Cоляпсус
 
08.12.17
15:47
(26) Где-то цикл в цикле забыли)
55 Cоляпсус
 
08.12.17
15:48
Отвлекли меня от написания рабочего кода, продолжу)
56 Cоляпсус
 
08.12.17
16:00
Запросом не получится или не получается. нет поля к которому можно было бы привязаться.
Через цикл что-то запутался, никак не выходит.
Вычитал, что это можно сделать рекурсивно, но не знаком с теорией как это реализовать
57 Cоляпсус
 
08.12.17
16:02
(45) Что имели ввиду?
58 Cоляпсус
 
08.12.17
16:07
МояТЗ = Новый ТаблицаЗначений;    
        МояТЗ = Данные.Скопировать();
        Индекс = 0;
             Для Индекс = 0 По 100 Цикл

            НоваяСтрока = МояТЗ.Добавить();
            ЗаполнитьЗначенияСвойств(НоваяСтрока, Данные[Индекс]);
            Индекс=Индекс+1;
            Если Индекс=100 Тогда
            СоздатьДокументКорректировки("СтоимостьОбъектовОС", МояТЗ);
                Индекс=0
            КонецЕсли;
        Конеццикла;
        Если Индекс>0 Тогда
            СоздатьДокументКорректировки("СтоимостьОбъектовОС", МояТЗ);
        КонецЕсли;
59 Cоляпсус
 
08.12.17
16:08
Подскажите пожалуйста, где собака порылась?
Спасибо
Большое
60 Табуретко
 
08.12.17
16:12
Данные[Индекс]
61 Табуретко
 
08.12.17
16:13
а по ходу тут все не так...
62 Табуретко
 
08.12.17
16:15
тебе предлагали заполнять ТЧ документа в цикле с счетчиком, а ты тут с ТЗ чето мудриш...
63 Cоляпсус
 
08.12.17
16:15
Да, извините. Так никто мне не сможет помочь. НЕ полные данные предоставил.
Данные - это исходная ТЗ состоящая из 230 строк
Поэтому и прошу помощи
64 Cоляпсус
 
08.12.17
16:16
А так нельзя?
65 Табуретко
 
08.12.17
16:17
покажи лучше СоздатьДокументКорректировки
66 Cоляпсус
 
08.12.17
16:18
Не совсем понял, что показать?
67 Табуретко
 
08.12.17
16:18
процедуру СоздатьДокументКорректировки()
68 Cоляпсус
 
08.12.17
16:19
Процедура СоздатьДокументКорректировки(ИмяРегистра, Данные)
    
    Если Данные.Количество() = 0 Тогда
        //ОбщегоНазначенияКлиентСервер.СообщитьПользователю("Расхождений по " + ?(ИмяРегистра = "СтоимостьОбъектовОС", "стоимости", "амортизации") + " не обнаружено");
        Возврат;
    КонецЕсли;
    
    Если Данные.Количество() > 100000 Тогда
        ОбщегоНазначенияКлиентСервер.СообщитьПользователю("Количество строк превышает 100000. Запись невозможна");
        Возврат;
    КонецЕсли;
    
    ДатаДвижений = КонецДня(ДатаСведения);
    
    Док = Документы.КорректировкаРегистров.СоздатьДокумент();
    Док.Организация = Организация;
    Док.Дата = ДатаДвижений;
    Док.УстановитьНовыйНомер();        
    Док.Комментарий = ИмяРегистра + " | документ создан автоматически | " + Формат(ТекущаяДата(), "ДЛФ=D");
        
    Таблица = Док.ТаблицаРегистровНакопления.Добавить();
    Таблица.Имя = ИмяРегистра;
    
    ОбновлениеИнформационнойБазы.ЗаписатьОбъект(Док);
        
    НаборЗаписей = РегистрыНакопления[ИмяРегистра].СоздатьНаборЗаписей();
    НаборЗаписей.Отбор.Регистратор.Установить(Док.Ссылка);
    
    Данные.Колонки.Добавить("Период");
    Данные.ЗаполнитьЗначения(ДатаДвижений, "Период");    
    НаборЗаписей.Загрузить(Данные);
        
    ОбновлениеИнформационнойБазы.ЗаписатьНаборЗаписей(НаборЗаписей);
    
    ДокументыСведения.Добавить(Док.Ссылка);
    
КонецПроцедуры
69 Табуретко
 
08.12.17
16:19
здесь оставляеш тока СоздатьДокументКорректировки("СтоимостьОбъектовОС", Данные);
70 Cоляпсус
 
08.12.17
16:22
простите за ...
здесь это где?
71 Табуретко
 
08.12.17
16:24
там откуда вызываеш эту процедуру...
72 Cоляпсус
 
08.12.17
16:27
понял
а в эту процедуру вставить код со счётчиком?
73 Cоляпсус
 
08.12.17
16:30
А в данной процедуре может как раз и встроить счётчик, что если Данные >= столько строкам, то создать первый док? Потом обнулить счётчик и дописать оставшиеся строки?
Может не прав...
74 1Садовник
 
08.12.17
16:31
(58) Вначале копируешь "Данные" в "МояТЗ" - Зачем?
В цикле добавляешь в "МояТЗ" еще 50 строк из "Данные".
После создания документа, "МояТЗ" очищается?
Зачем в этом цикле "Индекс = Индекс + 1" ?
75 Cоляпсус
 
08.12.17
16:33
Согласен не прав
76 Cоляпсус
 
08.12.17
16:38
(74) Это я неудачно экспериментировал, пытаясь понять почему стоки добавляет, а колонки не хочет брать из данных, видимо их отдельно надо добавлять
77 Табуретко
 
08.12.17
17:05
ок, процедуру СоздатьДокКорректировки не трогаем

за место (58) пишем примерно следующее...

    СчетчикВыгрузки = 0; //обьяви на всякий пожарный
    МассивСтрок = Новый Массив;
    Для каждого Стр Из Данные Цикл
        СчетчикВыгрузки = Стр.Индекс;
        Массив.Добавить(Стр);
        Если СчетчикВыгрузки % 99 = 0 Тогда //помни что индекс начинается с 0
            МояТЗ = Данные.Скопировать(МассивСтрок);
            СоздатьДокументКорректировки("СтоимостьОбъектовОС", МояТЗ);    
            МассивСтрок.Очистить();
        КонецЕсли;        
    КонецЦикла;
    
    Если СчетчикВыгрузки % 99 <> 0 Тогда
        МояТЗ = Данные.Скопировать(МассивСтрок);
        СоздатьДокументКорректировки("СтоимостьОбъектовОС", МояТЗ);    
    КонецЕсли;
78 Табуретко
 
08.12.17
17:17
сорь Массив.Добавить(Стр); --> МассивСтрок.Добавить(Стр);
79 Табуретко
 
08.12.17
17:28
или даже так...

    МассивСтрок = Новый Массив;
    Для каждого Стр Из Данные Цикл
        МассивСтрок.Добавить(Стр);
        Если МассивСтрок.Количество() % 100 = 0 Тогда
            МояТЗ = Данные.Скопировать(МассивСтрок);
            СоздатьДокументКорректировки("СтоимостьОбъектовОС", МояТЗ);    
            МассивСтрок.Очистить();
        КонецЕсли;        
    КонецЦикла;
    
    Если МассивСтрок.Количество() % 100 <> 0 Тогда
        МояТЗ = Данные.Скопировать(МассивСтрок);
        СоздатьДокументКорректировки("СтоимостьОбъектовОС", МояТЗ);    
    КонецЕсли;
80 Cоляпсус
 
08.12.17
17:33
(78) Да это я видел, понимаю машинально.
спасибо, почему сам никак не до пру((
(79) Наверное (ещё не проверил) будет правильнее, а то
СчетчикВыгрузки = Стр.Индекс; - говорит что Индекс ему не нравится, поле объекта не обнаружено
81 Cоляпсус
 
08.12.17
17:34
(79) ещё раз спасибо, самому стыдно)))
82 Табуретко
 
08.12.17
17:37
работает хоть?
83 Cоляпсус
 
08.12.17
17:38
Проверяю
84 Cоляпсус
 
08.12.17
17:50
Теоретически работает, проверить до конца пока не могу, потому что при создании документа ругается на поле период в Процедура СоздатьДокументКорректировки(ИмяРегистра, Данные)
Придётся с этим разбираться, приходится править. Но с этой обработкой так и происходит, вставляешь действие на что-то ругается. Уже всё поправил, два пункта только остались, но вот на них и встрял.
Наверное правильнее будет в самой процедуре код внести на ограничение записей, хотя не уверен, буду разбираться
спасибо ещё раз
85 Cоляпсус
 
08.12.17
17:51
Обработка не моя, написанная фрилансирами, как то вроде давно
86 Cоляпсус
 
08.12.17
17:51
(82) Спасибо