Имя: Пароль:
1C
 
Работа со Справочниками
0 egor
 
15.12.03
14:52
Есть справочник ТМЦ. В него нужно влить ТМЦ из dbf-ника. Сделал обработочку, к корневой - без проблем. Можно ли  и как раскидать обработкой эти ТМЦ в соответствующий папки справочника при заливке. Привязка идет по коду.
1 skunk
 
15.12.03
15:11
В принципе да, но это будет сильно тормозить. Если не проблема то делаешь в выгрузке еще одно поле ID родителя, или используешь ПолныйКод. Ну и соответственно обработку загрузки меняешь.
2 egor
 
15.12.03
15:24
Да в выгрузке поле не обязательно. Я и в обработке родителя могу найти (например: Код ТМЦ 20105МН00011, родитель код - 20105МН. Я отсекаю 5 последних цифр). Находить то группу я нахожу, а как запихнуть именно в эту папку новый элемент?!? Уже мозги варенные
3 skunk
 
15.12.03
15:29
Родитель = Спр.ТекущийЭлемент(); - Это найденый род. элемент
Спр.ИспользоватьРодителя(Родитель);
Спр.Новый();

Ну и далее там сам знаешь
4 Львенок
 
15.12.03
15:40
Ну скажешь тоже! Использовать родителя... Все еще проще:

ГрпРодитель=Спр.ТекущийЭлемент(); //ГрпРодитель - элемент справочника, являющийся группой.
Спр.Новый();
Спр.Родитель=ГрпРодитель; // Назначаем элементу родителя. Это быстрее, если работаем с одним элементом.
5 egor
 
15.12.03
15:58
Спасибо, я как раз этим и занимался. Просто вначале смутило, "Если метод применен для объекта, созданного функцией СоздатьОбъект, то данный параметр срабатывает при вызове метода Выбрать.". На практике все получилось, Еще раз сенкс
6 egor
 
15.12.03
16:14
Вообще то я реализовал что-то вроде (3).Сработало. 1000 ТМЦ записало за 3,5 мин. У меня их сейчас 3500 наименований нужно втянуть.. Но в будущем есть вариант что будет еще больше.
(4)Попробую паралельно сделать и сравню производительность. Спасибо
7 skunk
 
15.12.03
16:57
Для цикла сделай так
Спр.ИспользоватьРодителя(Родитель);
Цикл
   Спр.Новый();
КонецЦикла;
Пр сути должен быть быстрее чем каждый раз
Спр.Родитель = Родитель
По моему даже на мисте где-то про это говориться.
8 Волшебник
 
15.12.03
21:21
Я думаю, скорости это сильно не прибавит.
9 skunk
 
15.12.03
22:41
Чтоб не спорить проведем эксперимент.
Я написал две обработки
speed1
//*******************************************
Процедура Сформировать()
 Спр = СоздатьОбъект("Справочник.Номенклатура");
 Старт = _GetPerformanceCounter();
   Для х = 1 По 100 Цикл
   Спр.Новый();
   Спр.Родитель = Родитель;
   Спр.Записать();
 КонецЦикла;
 Финиш = _GetPerformanceCounter();
 Сообщить(Финиш - Старт);
КонецПроцедуры

speed2
//*******************************************
Процедура Сформировать()
 Спр = СоздатьОбъект("Справочник.Номенклатура");
 Старт = _GetPerformanceCounter();
 Спр.ИспользоватьРодителя(Родитель);
 Для х = 1 По 100 Цикл
   Спр.Новый();
   Спр.Записать();
 КонецЦикла;
 Финиш = _GetPerformanceCounter();
 Сообщить(Финиш - Старт);
КонецПроцедуры

Далее создал четыре абсолютно одинаковые базы, две – локально и две – сетевые. Торговля стандартной поставки. И провел три теста. Запуск осуществлялся в монопольном режиме.
Test1 – В пустом каталоге создавал группу 1, куда добавил сто новых элементов.
Test2 – В полученном справочнике создал группу 2, куда добавил сто новых элементов.
Test3 – К группе 1 добавил еще сто новых элементов.

Результат:
Test1(локально)
speed1 18888
speed2 16274

Test2(локально)
speed1 20427
speed2 17310

Test3(локально)
speed1 20313
speed2 17072

Test1(сеть)
speed1 31071
speed2 28508

Test2(сеть)
speed1 41443
speed2 35698

Test3(локально)
speed1 53748
speed2 44368

Думаю последний тест, для человека самый актуальный.
10 Волшебник
 
15.12.03
22:51
Да, ускорение около 15-20%.

А теперь попробуй поменять порядок выполнения тестов. Может там кэш срабатывает и тот, кто выполняется вторым всегда выигрывает. По хорошему надо перезагружаться между тестами.
11 skunk
 
15.12.03
22:57
Так и было. Из эсины выходил только систему не перезапускал.
А по хорошему надо было проводить по нескольку тестов (обычно говрят по 10, но чем больше тем лучше) и говорить среднее, кому надо пусть проводит.
12 Львенок
 
15.12.03
23:04
Разумеется с твоем примере первый вариант быстрее, это и ежу понятно. У тебя элементы последовательно создаются в одной группе. А ты теперь то же самое проверь, когда элементы создаются вразнобой, в случайных группах.
___
Искренне Ваш, Львенок.
13 skunk
 
15.12.03
23:43
Ну скажешь тоже! Использовать родителя... Все еще проще:

ГрпРодитель=Спр.ТекущийЭлемент(); //ГрпРодитель - элемент справочника, являющийся группой.
Спр.Новый();
Спр.Родитель=ГрпРодитель; // Назначаем элементу родителя. Это быстрее, если работаем с одним элементом

я тебе доказал что не всегла проще
14 Львенок
 
16.12.03
07:47
Ты видел мой комментарий в присвоении родителя? Я же сказал, когда с одним элементом.Т.е. когда за один раз в одной группе создаем один элемент. А ты запихал присвоение внутрь цикла, совершенно очевидно, что любой лишьний оператор внутри цикла существенно увеличивает время выполнения. Если бы ты в тесте №1 Спр.ИспользоватьРодителя(Родитель) тоже бы записал внутрь цикла, получился бы тот случай, который я имел ввиду.
___
Искренне Ваш, Львенок.
15 skunk
 
16.12.03
08:05
А зачем это делать, прочитай про ИспользоватьРодителя документацию там русским языком говориться, что, если говорить грубо, после этого Спр.Родитель ставиться автоматический.
16 Львенок
 
16.12.03
10:19
Еще раз поясню. Бывают случаи премерно такого порядка:
Грп[3]={Грп1, Грп2, Грп3};
Цикл
 Элемем=ТекущийЭлемент();
 ГрпТек=Грп[RND*3]; //Т.е. группа в которую будем писать заранее не известна (в реальном примере это эквивалентно тому, что не отсортированы заранее элементы по будующей своей Группе)

 Если Вариант=skunk Тогда
   Спр.ИспользоватьРодителя(ГрпТек); //Приходится делать внутри цикла, т.к. мы не можем вынести это за его пределы
   Спр.Новый();
   Спр.Записать();
 ИначеЕсли Вариант=Львенок Тогда
   Спр.Новый();
   Спр.Родитель=ГрпТек; //В любом случае внутри цикла
   Спр.Записать();
 КонецЕсли;
КонецЦикла;

А вот теперь смотри. В контексте данной темы, элементы можно заранее отсортировать по предполагаемой группе "220105МН00011" - название группы (220105МН) идет в начале названия элемента, и можно сразу порядочить по наименованию. Твой вариант будет действительно быстрее, т.к. можно сделать, чтобы ИспользоватьРодителя() выполнялось не на каждом шаге цикла.
А если бы было наоборот? Названия элементов группы были бы "00011220105МН"? Имя группы мы можем выделить из имени элемента, но заранее отсортировать по нему, не создавая дополнииельные таблицы мы не можем. Тогда, обрабатывая элементы в цикле (допустим также отсортированные по наименованию), мы получаем группы в разнобой, и должны будем использовать ИспользоватьРодителя() на каждом шаге. Логично? И вот в такой ситуации, Родитель=ГрпТек будет предпочтительнее. Так вот я говорил именно об этом.
___
Искренне Ваш, Львенок.
17 skunk
 
16.12.03
10:56
Без коментариев. Львенок я уже устал. Пускай человек сам решит, что ему лучше.
18 Львенок
 
16.12.03
11:33
Ага. Я тоже. ;) Главное, все правы. Виноватых нет. ;)
___
Искренне Ваш, Львенок.
19 egor
 
16.12.03
11:41
Мужики, спасибо за развитие темы. Вчера перед окончанием рабочего дня залил справочник. ДБФ-ник присылают нам свыше. Элементы явно не отсортированы, сортировать их мне просто не дают времени. Так что цикл у меня стоит только на переборе ДБФ-ника. По коду елемента нахожу группу и туда ее впихиваю.

Пока ДБФ.Следующая() = 1 Цикл
 Спр.НайтиПоКоду(Лев(СокрЛП(ДБФ.kod),СтрДлина(СокрЛП(ДБФ.kod))-5),0);
 Если Спр.ЭтоГруппа() = 1 Тогда
   Спр.ИспользоватьРодителя(Спр.ТекущийЭлемент());
   Спр.Новый();
   Спр.Код = ДБФ.kod;
   Спр.Наименование = ДБФ.name;
   Спр.ЕдИзм = ДБФ.od_izm;
   Спр.Записать();
 КонецЕсли;
КонецЦикла;
20 skunk
 
16.12.03
16:35
Тут конечно надо смотреть, как у тебя идет заполнение источника данных, то есть самого dbf. Если, ты берешь справочник целиком и тащищь его в другую конфу, то здесь скорее всего Львенок будет прав, и его код отработает быстрее.
21 egor
 
16.12.03
17:05
Согласен
Компьютер — устройство, разработанное для ускорения и автоматизации человеческих ошибок.