|   |   | 
| 
 | v7: Объединить две ТЗ | ☑ | ||
|---|---|---|---|---|
| 0
    
        Arbuz 31.01.19✎ 15:18 | 
        Есть две ТЗ. Состав колонок совпадает частично. В ТЗ_2 есть колонка "Ключ" с уникальным натуральным числовым значением, напр 4 строки - "2,3,7,100". Нужно в ТЗ_1 заменить значения в совпадающих по имени колонках из ТЗ_2, где номер строки ТЗ_1 = значению Ключ ТЗ_2. Удалить строки ТЗ_1, номера которых нет в колонке Ключ ТЗ_2. Добавить в ТЗ_1 строки из ТЗ_2, где Ключ > начального количества строк ТЗ_1.
 dbf, 1cpp, formex, 1sqlite Пока что в голову ничего лучше, кроме двойного прохода с промежуточной ТЗ_3 не приходит. | |||
| 1
    
        VladZ 31.01.19✎ 15:30 | 
        Вот тут почитай: http://www.1cpp.ru/docum/html/IndexedTable.html     | |||
| 2
    
        VladZ 31.01.19✎ 15:31 | 
        Вариант №2: сразу получать данные в нужном виде.     | |||
| 3
    
        Arbuz 31.01.19✎ 15:37 | 
        (1) Почитал. Не просветляет. Что, надо будет получать разность, потом пересечение и объединять?     | |||
| 4
    
        Arbuz 31.01.19✎ 15:39 | 
        (2) Сразу никак, данные из разных источников, полученные в разное время     | |||
| 5
    
        VladZ 31.01.19✎ 15:50 | 
        (3) Почитай про ВнутреннееСоединение и ЛевоеСоединение.     | |||
| 6
    
        Arbuz 31.01.19✎ 15:53 | 
        (5) Воу! спс, у меня локально какие-то старинные доки на ИТЗ     | |||
| 7
    
        Kigo_Kigo 31.01.19✎ 16:21 | 
        (5) А ничего что это клюшки?     | |||
| 8
    
        Evgenchik 31.01.19✎ 16:23 | 
        (7) Ничего     | |||
| 9
    
        trad 31.01.19✎ 16:27 | 
        (7) на клюшки ТС наложены магические руны     | |||
| 10
    
        Svetka 31.01.19✎ 18:08 | 
        (0) Да, без промежуточной ТЗ и перебора тз1 и тз2 - никак, только если извлекать данные в ключ как - то иначе.    
 ТЗ3 =СоздатьОбъект("ТаблицаЗначений"); ТЗ3.Очистить(); ТЗ3.НоваяКолонка("строкаТЗ1"); ТЗ2.ВыбратьСтроки(); Пока ТЗ2.ПолучитьСтроку()= 1 Цикл НомСтр_тз1 = ТЗ2.Ключ; Числ = СтрЧислоВхождений(СокрЛП(НомСтр_тз1),","); Вх1 = Найти(СокрЛП(НомСтр_тз1),","); Для в= 1 По Числ+1 Цикл НомПл=""; Если в=1 Тогда НомПл = Число(Лев(СокрЛП(НомСтр_тз1),Вх1-1)); Ост = Сред(СокрЛП(НомСтр_тз1),Вх1+1); Вх1 = Найти(СокрЛП(Ост),","); ИначеЕсли в=Числ+1 Тогда НомПл = Число(Сред(СокрЛП(Ост),Вх1+1)); Иначе НомПл = Число(Лев(СокрЛП(Ост),Вх1-1)); Ост = Сред(СокрЛП(Ост),Вх1+1); Вх1 = Найти(СокрЛП(Ост),","); КонецЕсли; ТЗ3.НоваяСтрока(); ТЗ3.строкаТЗ1 = НомПл; Если ТЗ1.ПолучитьСтрокуПоНомеру(НомПл) = 1 Тогда //строка найдена ТЗ1.Колонка1 = ТЗ2.Колонка1; ТЗ1.Колонка2 = ТЗ2.Колонка2; ТЗ1.КолонкаN = ТЗ2.КолонкаN; Иначе Если ТЗ1.КоличествоСтрок()<НомПл Тогда //строка создается ТЗ1.НоваяСтрока(); ТЗ1.Колонка1 = ТЗ2.Колонка1; ТЗ1.Колонка2 = ТЗ2.Колонка2; ТЗ1.КолонкаN = ТЗ2.КолонкаN; КонецЕсли; КонецЕсли; КонецЦикла; КонецЦикла; ТЗ1.ВыбратьСтроки(); Пока ТЗ1.ПолучитьСтроку() = 1 Цикл ~метка: стр = ""; Если ТЗ3.НайтиЗначение(ТЗ1.НомерСтроки,стр,"строкаТЗ1") = 0 Тогда //строка удаляется ТЗ1.УдалитьСтроку(); Если ТЗ1.НомерСтроки <> 0 Тогда Перейти ~метка; КонецЕсли; КонецЕсли; КонецЦикла; | |||
| 11
    
        Arbuz 31.01.19✎ 18:17 | 
        (10) Зря вы так. Все получилось через ИТЗ.ПравоеСоединение. 30 строк кода. И то из-за того, что пришлось извратиться с циклом по первой ИТЗ для ЗаполнитьКолонку("НомерСтроки"). На таблицах до десятка тысяч строк - до полутора сотен мсек.     | |||
| 12
    
        VladZ 31.01.19✎ 18:26 | 
        (10) Однако! Использование меток - дурной тон.
 В данном случае достаточно было использовать "Продолжить" | |||
| 13
    
        Aleksandr N 31.01.19✎ 19:01 | 
        (12) А в семерке оно есть? А то я не умею в 7.7.     | |||
| 14
    
        Arbuz 01.02.19✎ 11:46 | 
        (13) конечно есть
 (0) кому интересно получилось так: 
Вот бы ещё от цикла по ИТЗ1 избавиться. Индекс по умолчанию как раз по номеру строки есть, но вот задать "НомерСтроки" в первом параметре Join'а нельзя к сожалению. | |||
| 15
    
        Arbuz 01.02.19✎ 11:52 | 
        +(14) упс.
 _ИТЗ1.Выгрузить(ТЗ1); конечно же | |||
| 16
    
        MadDAD 01.02.19✎ 13:16 | 
        (15) А если вот это:
 [code] Для _СчетчикЦикла = 1 По _ИТЗ1.КоличествоСтрок() Цикл _аВрем = _аВрем + _СчетчикЦикла + ","; КонецЦикла; Если _аВрем = "" Тогда глОтладка("Пустая ИТЗ1"); Возврат; КонецЕсли; _КоличествоСтрокТЗ = СоздатьОбъект("СписокЗначений"); _КоличествоСтрокТЗ.ИзСтрокиСРазделителями(Лев(_аВрем, СтрДлина(_аВрем) - 1)); _ИТЗ1.ЗаполнитьКолонку(, "НомерСтрокиТЗ", _КоличествоСтрокТЗ); _КоличествоСтрокТЗ = ""; [/code] заменить на это? [code] _ИТЗ1.ВыбратьСтроки() Пока _ИТЗ1.ПолучитьСтроку() = 1 Цикл _ИТЗ1.НомерСтрокиТЗ = _ИТЗ1.НомерСтроки; КонецЦикла; [/code] | |||
| 17
    
        Arbuz 01.02.19✎ 17:10 | 
        (16) Дык, собственно, это и было заменено в обратном порядке, для ускорения. Чтобы не перебирать в цикле строки ИТЗ. И в Вашем коде не хватает
 _ИТЗ1.НоваяКолонка("НомерСтрокиТЗ"); перед циклом. Кстати в доках не документировано, что ЗаполнитьКолонку() создаёт её при отсутствии. Интересно, можно ли вообще избавиться от этого цикла? | 
 
 | Форум | Правила | Описание | Объявления | Секции | Поиск | Книга знаний | Вики-миста |