Имя: Пароль:
1C
1С v8
Типизация колонок Таблицы значения
0 Ruslan_
culeiman
 
22.04.17
16:27
Приветствую, есть ТЗ с кучей колонок, как можно быстро их все типизировать, чтобы потом запихать в запрос? Или нужно создать ТЗ, создать каждую колонку и типизировать, а потом только в запрос?

Либо необязательно в запрос, просто нужен отбор "В Иерархии" по этой ТЗ.
1 Ruslan_
culeiman
 
22.04.17
16:29
(0) Либо "в списке"
2 TormozIT
 
гуру
22.04.17
16:30
Из подсистемы ИР (ОбщийМодуль.ирОбщий)

// Получает копию таблицы значений с минимальными типами колонок для содержания всех данных.
// Параметры:
//   ТаблицаДанных - ТаблицаЗначений
//   СужатьТолькоПроизвольныеКолонки - Булево - обрабатывать только колонки с пустым (произвольным) типом
//   ИмяКолонки - Строка - нужна только эта колонка
//
Функция ПолучитьТаблицуСМинимальнымиТипамиКолонокЛкс(Знач ТаблицаДанных, СужатьТолькоПроизвольныеКолонки = Ложь, ИмяКолонки = "") Экспорт
    
    #Если Сервер И Не Сервер Тогда
        ТаблицаДанных = Новый ТаблицаЗначений;
    #КонецЕсли
    ОставляемыеКолонки = "";
    СужаемыеКолонки = Новый Массив();
    Для Каждого КолонкаДанных Из ТаблицаДанных.Колонки Цикл
        Если ЗначениеЗаполнено(ИмяКолонки) И Не СтрокиРавныЛкс(ИмяКолонки, КолонкаДанных.Имя) Тогда
            Продолжить;
        КонецЕсли;
        Если Истина
            И СужатьТолькоПроизвольныеКолонки
            И КолонкаДанных.ТипЗначения.Типы().Количество() > 0
        Тогда
            ОставляемыеКолонки = ОставляемыеКолонки + "," + КолонкаДанных.Имя;
        Иначе
            СужаемыеКолонки.Добавить(КолонкаДанных);
        КонецЕсли;
    КонецЦикла;
    //Состояние("Оптимизация типов колонок");
    НовыеКолонки = Новый Структура;
    МетаданныеТаблицыИзменены = Ложь;
    Индикатор = ирОбщий.ПолучитьИндикаторПроцессаЛкс(СужаемыеКолонки.Количество(), "Анализ колонок");
    Для Каждого КолонкаДанных Из СужаемыеКолонки Цикл
        ирОбщий.ОбработатьИндикаторЛкс(Индикатор);
        Типы = Новый Массив;
        ТаблицаКолонки = ТаблицаДанных.Скопировать(, КолонкаДанных.Имя);
        ТаблицаКолонки.Свернуть(КолонкаДанных.Имя);
        СтароеОписаниеТипов = КолонкаДанных.ТипЗначения;
        Для Каждого СтрокаДанных Из ТаблицаКолонки Цикл
            ТипЗначения = ТипЗнч(СтрокаДанных[КолонкаДанных.Имя]);
            Если Истина
                И ТипЗначения <> Тип("Неопределено")
                И Типы.Найти(ТипЗначения) = Неопределено
            Тогда
                Типы.Добавить(ТипЗначения);
            КонецЕсли;
        КонецЦикла;
        Если Типы.Количество() = 0 Тогда
            Типы = КолонкаДанных.ТипЗначения.Типы();
            Если Типы.Количество() = 0 Тогда
                Типы.ДОбавить(Тип("Булево"));
                Типы.ДОбавить(Тип("Число"));
            КонецЕсли;
            // Чтобы от супертипов через точку не было много соединений, оставляем только 2 типа
            Пока Типы.Количество() > 2 Цикл
                Типы.Удалить(0);
            КонецЦикла;
        КонецЕсли;
        Если Типы.Количество() <> СтароеОписаниеТипов.Типы().Количество() Тогда
            МетаданныеТаблицыИзменены = Истина;
        КонецЕсли;
        НовоеОписаниеТипов = Новый ОписаниеТипов(Типы, , , СтароеОписаниеТипов.КвалификаторыЧисла, СтароеОписаниеТипов.КвалификаторыСтроки, СтароеОписаниеТипов.КвалификаторыДаты);
        НовыеКолонки.Вставить(КолонкаДанных.Имя, НовоеОписаниеТипов);
    КонецЦикла;
    ирОбщий.ОсвободитьИндикаторПроцессаЛкс();
    Если МетаданныеТаблицыИзменены Тогда
        Если ОставляемыеКолонки <> "" Тогда
            ТипизированнаяТаблица = ТаблицаДанных.Скопировать(, ОставляемыеКолонки);
        Иначе
            ТипизированнаяТаблица = Новый ТаблицаЗначений;
        КонецЕсли;
        Для Каждого КлючИЗначение Из НовыеКолонки Цикл
            ТипизированнаяТаблица.Колонки.Добавить(КлючИЗначение.Ключ, КлючИЗначение.Значение, ТаблицаДанных.Колонки[КлючИЗначение.Ключ].Заголовок);
        КонецЦикла;
        Индикатор = ирОбщий.ПолучитьИндикаторПроцессаЛкс(ТаблицаДанных.Количество() / 100, "Оптимизация таблицы");
        Для Индекс = 0 По ТаблицаДанных.Количество() - 1 Цикл
            Если Индекс % 100 = 0 Тогда
                ирОбщий.ОбработатьИндикаторЛкс(Индикатор);
            КонецЕсли;
            Если ОставляемыеКолонки <> "" Тогда
                СтрокаТипизированнойТаблицы = ТипизированнаяТаблица[Индекс];
            Иначе
                СтрокаТипизированнойТаблицы = ТипизированнаяТаблица.Добавить();
            КонецЕсли;
            ЗаполнитьЗначенияСвойств(СтрокаТипизированнойТаблицы, ТаблицаДанных[Индекс]);
        КонецЦикла;
        ирОбщий.ОсвободитьИндикаторПроцессаЛкс();
    Иначе
        ТипизированнаяТаблица = ТаблицаДанных;
    КонецЕсли;
    Результат = ТипизированнаяТаблица;
    Возврат Результат;
    
КонецФункции