gifts2017

Удаление строк из таблицы значений по критерию

Опубликовал shard (shard) в раздел Программирование - Практика программирования

Удаление строк из таблицы значений по критерию
На днях задали вопрос: а как удалить строки из таблицы значений по какому-то условию? вопрос конечно простой, но когда "горит", то... поэтому всегда под рукой следующий алгоритм:
всего=ТЗ.Количествострок();		
сч=1;		

пока сч<=всего цикл		
	

состояние

("Обработка строк: "+строка(сч)+" из "+строка(всего));
ТЗ.Получитьстрокупономеру(сч);
Если   <условие>   тогда

ТЗ.Удалитьстроку(сч);
		

всего = всего -1;
	

Иначе

сч=сч+1;
	
КонецЕсли;	
Конеццикла;
Может кто как-то еще сие выполняет?

См. также

Подписаться Добавить вознаграждение

Комментарии

1. Князев Евгений Юрьевич (noblekey) 05.11.08 11:21
Можно так
СтруктураОтбора = Новый Структура("Наименование реквизита", Егозначение);// задаем условия
МассивСтрок = ЭтотОбъект.Товары.НайтиСтроки(СтруктураОтбора);
Для Каждого ЭлементМассив Из МассивСтрок Цикл
ЭтотОбъект.Товары.Удалить(ЭлементМассив); //удаляем строки
КонецЦикла;
alexandrmishinn; +1 Ответить 2
2. Lomok (lomok) 05.11.08 11:31
Эта тема по моему уже затерта до дыр.
Мне больше всего понравился способ от NS.
3. Епрст (Ёпрст) 05.11.08 11:44
Автор, выкинь свой алгоритм в топку, смотри, как надо:

http://www.sinor.ru/~my1c/knowhow/delstrtz.html
4. Епрст (Ёпрст) 05.11.08 11:46
(2) Мне от TDV больше радует...
5. shard (shard) 05.11.08 11:54
(1) под семерку не пойдет ;)
(3) благодарю за ссылку
6. shard (shard) 05.11.08 12:38
проверил код из темы в (3). неожиданно хороший результат по второму набору (все удовлетворяют условию)))). вывод - неплохо будет работать когда процент удаляемых значений мал из-за большого времени отработки строки "ТЗ.Удалитьстроку(сч);"
7. Алексей Константинов (alexk-is) 05.11.08 15:26
Я шесть лет назад участвовал в этом конкурсе...
Поэтому есть одно, но существенное замечание. Тест на 10 элементах не показывает ошибки сортировки. Ошибки вылазят на 20 элементах теста. Т.е. изменяется первоначальный порядок строк...

Предлагаю вариант проверки на 20 строках и 2 новых способа от alexk aka alexk-is:

Код
// Прошу прощения на несколько сумбурно организованную программу.
// Она периодически дополняется разными штуками, которые "в начале пути" не предусматривались.
// Переписывать заново нет времени да и особого желания - работает и ладно ...

Перем ТЗ;  // на этой таблице все и проверяем
Перем ТЗРезультаты;         
Перем БылПрерван;
Перем НомерНабора;

//*******************************************
// вспомогательная процедура ROM 
Функция СложитьТаблицы(ТЗ1,ТЗ2)
   Если ТЗ2=0 Тогда
      Возврат ТЗ1;
   КонецЕсли;
   Если ТЗ1=0 Тогда
      Возврат ТЗ2;
   Иначе
      ДоЭтогоСтрок=ТЗ1.КоличествоСтрок();
      Если ТЗ2.КоличествоСтрок()<>0 Тогда
         Для Ном=1 По ТЗ2.КоличествоСтрок() Цикл
            ТЗ1.НоваяСтрока();
         КонецЦикла;
         ТЗ1.Заполнить(ТЗ2,ДоЭтогоСтрок+1);
      КонецЕсли;
      Возврат ТЗ1;
   КонецЕсли;
КонецФункции                                
//*******************************************
Функция УсловиеВыполняется(Значение)
    Возврат ?(Значение<МаксЗнач/2,1,0); 
КонецФункции
//******************************************* // здесь по аналогии добавьте Ваш вариант обработки
Функция ФильтроватьТЗ(Вариант="")         
   Перем ТЗ_СЛУЖ,СтрокКода;
   Перем массив[1000000]; // для NefedovSergey
   СтрокКода=0;    
   Если Вариант="mszsuz" Тогда    // ************************************ mszsuz 18 строк 
      // оптимизированный avb вариант, примечания его же
      КолСтр=ТЗ.КоличествоСтрок();
      ТЗ.НоваяКолонка("СЛУЖ_КОЛ"); //если тип, вообще, не определять работает быстрее
      ТЗ.Выбратьстроки();
      НачСтрока=0;
      Пока ТЗ.Получитьстроку()=1 Цикл
         Если УсловиеВыполняется(ТЗ.К)=1 Тогда
            НачСтрока=НачСтрока+1;
            ТЗ.СЛУЖ_КОЛ=1; //номер строки тоже необязательно
         КонецЕсли;
      КонецЦикла;                      
      ТЗ.Сортировать("СЛУЖ_КОЛ"); //"плюс" похоже не тормозит, но я убрал 
      ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
      Если НачСтрока=0 Тогда
         ТЗ.УдалитьСтроки(); 
      ИначеЕсли НачСтрока<=КолСтр тогда
         ТЗ.Выгрузить(ТЗ_СЛУЖ,КолСтр-НачСтрока+1); //работает быстрее, если третий параметр не указывать, а здесь его как раз можно опустить 
         ТЗ_СЛУЖ.Выгрузить(ТЗ);
      КонецЕсли; 
      СтрокКода=18;
   ИначеЕсли Вариант="VVS" тогда // ************************************ VVS  
      КолСтр=ТЗ.КоличествоСтрок();
      ТЗ.НоваяКолонка("СЛУЖ_КОЛ","Число",СтрДлина(Строка(КолСтр))+1);
      ТЗ.Выбратьстроки();
      НачСтрока=0;
      Пока ТЗ.Получитьстроку()=1 Цикл
         Если УсловиеВыполняется(ТЗ.К)=1 Тогда
            НачСтрока=НачСтрока+1;
            ТЗ.СЛУЖ_КОЛ=-ТЗ.НомерСтроки;
         КонецЕсли;
      КонецЦикла;
      Если НачСтрока*2<КолСтр Тогда
         ТЗ.Сортировать("-СЛУЖ_КОЛ");
         ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
         Если НачСтрока=0 Тогда
            ТЗ.УдалитьСтроки();
         ИначеЕсли НачСтрока<КолСтр тогда
            ТЗ.Выгрузить(ТЗ_СЛУЖ,КолСтр-НачСтрока+1,КолСтр);
            ТЗ_СЛУЖ.Выгрузить(ТЗ);
         КонецЕсли;
      Иначе
         ТЗ.Сортировать("+СЛУЖ_КОЛ");
         ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
         Если НачСтрока=0 Тогда
            ТЗ.УдалитьСтроки();
         ИначеЕсли НачСтрока<КолСтр тогда
            ТЗ.Выгрузить(ТЗ_СЛУЖ,1,НачСтрока);
            ТЗ_СЛУЖ.Выгрузить(ТЗ);
         КонецЕсли;
      КонецЕсли;
      СтрокКода=29;
   ИначеЕсли Вариант="Serpent" Тогда   // 07.06.02 ************************************ Serpent  
      ТЗ_Получ = СоздатьОбъект("ТаблицаЗначений");
      ТЗ.Выгрузить(ТЗ_Получ,1,1);
      ТЗ_Получ.УдалитьСтроки();
      СЗ_Служ = СоздатьОбъект("СписокЗначений");
      НачалоБлока = 0;
      ТЗ.Выбратьстроки();
      Пока ТЗ.Получитьстроку()=1 Цикл
         Если УсловиеВыполняется(ТЗ.К)=1 Тогда
            Если НачалоБлока = 0 Тогда
               // начинаем   новый блок данных
               НачалоБлока = ТЗ.НомерСтроки;
            КонецЕсли;
         Иначе
            // запишем блок данных
            Если НачалоБлока > 0 Тогда
               НомерПервойСтрокиБлока = ТЗ_Получ.КоличествоСтрок() + 1;
               НовыйРазмерТаблицы = ТЗ.НомерСтроки - НачалоБлока + ТЗ_Получ.КоличествоСтрок();
               ТЗ_Получ.КоличествоСтрок(НовыйРазмерТаблицы);
               ТЗ.Выгрузить(ТЗ_Служ,НачалоБлока,ТЗ.НомерСтроки-1);
               ТЗ_Получ.Заполнить(ТЗ_Служ,НомерПервойСтрокиБлока);
               НачалоБлока = 0;
            КонецЕсли;
         КонецЕсли;
      КонецЦикла;
      Если НачалоБлока > 1 Тогда
         // остался последний блок данных -    перенесем его в ТЗ
         НомерПервойСтрокиБлока = ТЗ_Получ.КоличествоСтрок() + 1;
         НовыйРазмерТаблицы = МаксЗнач -   НачалоБлока + ТЗ_Получ.КоличествоСтрок() + 1;
         ТЗ_Получ.КоличествоСтрок(НовыйРазмерТаблицы);
         ТЗ.Выгрузить(ТЗ_Служ,НачалоБлока,МаксЗнач);
         ТЗ_Получ.Заполнить(ТЗ_Служ,НомерПервойСтрокиБлока);
      ИначеЕсли НачалоБлока = 1 Тогда
         // вся ТЗ удовлетворяет условию
         Возврат 35;
      КонецЕсли;
      Если ТЗ_Получ.КоличествоСтрок()=0 Тогда
         ТЗ.УдалитьСтроки(); 
      Иначе
         ТЗ_Получ.Выгрузить(ТЗ);
      КонецЕсли;
      СтрокКода=35;
   ИначеЕсли Вариант="Diamond" Тогда // ************************************ Diamond 6 строк
      Кол=ТЗ.КоличествоСтрок();
      Для А=-Кол По -1 Цикл
         Если УсловиеВыполняется(ТЗ.ПолучитьЗначение(-А,"К"))=0 Тогда
            ТЗ.УдалитьСтроку(-А);
         КонецЕсли;
      КонецЦикла;
      СтрокКода=6;
   ИначеЕсли Вариант="GaninY" Тогда // ************************************ GaninY 14 строк
      ТЗ1=СоздатьОбъект("ТаблицаЗначений");
      ТЗ.Выгрузить(ТЗ1,?(ТЗ.КоличествоСтрок()=0,"",1),?(ТЗ.КоличествоСтрок()=0,"",1));
      ТЗ1.УдалитьСтроки();
      Колонок=ТЗ.КоличествоКолонок();
      ТЗ.ВыбратьСтроки();
      Пока ТЗ.ПолучитьСтроку()=1 Цикл
          Если УсловиеВыполняется(ТЗ.К)=1 Тогда
              ТЗ1.НоваяСтрока();
            Для Нум=1 По Колонок Цикл
                ТЗ1.УстановитьЗначение(ТЗ1.НомерСтроки,Нум,ТЗ.ПолучитьЗначение(ТЗ.НомерСтроки,Нум));
            КонецЦикла;
          КонецЕсли;
      КонецЦикла;
      ТЗ=ТЗ1;
      СтрокКода=14;
   ИначеЕсли Вариант="slavic" Тогда // 15.09.2002 ************************************ slavic
      с1=0; 
      с2=0; 
      кк=Тз.КоличествоКолонок(); 
      Тз.ВыбратьСтроки(); 
      Пока Тз.ПолучитьСтроку()=1 Цикл 
         с1=с1+1; 
         Если УсловиеВыполняется(Тз.К)=1 Тогда 
            с2=с2+1; 
            Если с2<с1 Тогда 
               Для к=1 По кк Цикл 
                  Тз.УстановитьЗначение(с2,к,Тз.ПолучитьЗначение(с1,к)); 
               КонецЦикла; 
            КонецЕсли; 
         КонецЕсли; 
      КонецЦикла; 
      Тз.КоличествоСтрок(с2); 
      СтрокКода=16;
   ИначеЕсли Вариант="Rom" Тогда   // 06,06,2002 ************************************ Rom
      ИнтервалыУдаления=СоздатьОбъект("СписокЗначений");
      ИнтервалыСохранения=СоздатьОбъект("СписокЗначений");
      ПерваяПозиция=1;
      УсловиеВыполнено=0;
      ВсегоСтрок=ТЗ.КоличествоСтрок();
      Для Ном=1 По ВсегоСтрок Цикл
         ТекущееУсловие=УсловиеВыполняется(ТЗ.ПолучитьЗначение(Ном,"К"));
         Если УсловиеВыполнено<>ТекущееУсловие Тогда
            // сменился флаг
            Если УсловиеВыполнено=0 Тогда
               // группа удаляемых элементов закончилась
               // Ном - первый не удаляемый
            Иначе
               // группа нормальных элементов закончилась
               // Ном - первый удаляемый
               ИнтервалыСохранения.ДобавитьЗначение(ПерваяПозиция,(Ном-1));
            КонецЕсли;
            ПерваяПозиция=Ном;
            УсловиеВыполнено=ТекущееУсловие;
         КонецЕсли;
      КонецЦикла;
      Если УсловиеВыполнено=0 Тогда
         // группа удаляемых элементов не закончилась
         // Ном - первый не удаляемый
      Иначе
         ИнтервалыСохранения.ДобавитьЗначение(ПерваяПозиция,(ВсегоСтрок));
      КонецЕсли;
      РезТЗ=0;
      ПозицияПо="";
      // теперь скопируем интервалы
      Для Ном=1 По ИнтервалыСохранения.РазмерСписка() Цикл
         ПозицияС=ИнтервалыСохранения.ПолучитьЗначение(Ном,ПозицияПо);
         ПозицияПо=Число(ПозицияПо);
         НоваяТЗ=СоздатьОбъект("ТаблицаЗначений");
         ТЗ.Выгрузить(НоваяТЗ,ПозицияС,ПозицияПо);
         РезТЗ=СложитьТаблицы(РезТЗ,НоваяТЗ);
      КонецЦикла;
      Если РезТЗ=0 Тогда
         ТЗ.УдалитьСтроки();
      Иначе
         РезТЗ.Выгрузить(ТЗ);
      КонецЕсли;  
      СтрокКода=34;
   ИначеЕсли Вариант="Чиканук" Тогда  // 21.06.02
      ГдеНеверный=0;
      ГдеВерный=0;
      ТЗ.НоваяКолонка("СЛУЖ_КОЛ","Число",СтрДлина(Строка(КолСтр))+1);
      СтрокаКолонок="";
      КоличествоКолонок=ТЗ.КоличествоКолонок();
      Для Счт=1 По КоличествоКолонок Цикл
         СтрокаКолонок=СтрокаКолонок+Счт+", ";
      КонецЦикла;
      ТЗ.Выбратьстроки();
      Пока ТЗ.Получитьстроку()=1 Цикл
         Если УсловиеВыполняется(ТЗ.К)=1 Тогда
            ТЗ.СЛУЖ_КОЛ=ТЗ.НомерСтроки;
            ГдеВерный=?(ГдеВерный=0,ТЗ.НомерСтроки,ГдеВерный);
         Иначе
            ГдеНеверный=?(ГдеНеверный=0,ТЗ.НомерСтроки,ГдеНеверный);
         КонецЕсли;
      КонецЦикла;
      Если ГдеВерный=0 Тогда
         ТЗ.УдалитьСтроки();
      ИначеЕсли ГдеНеверный>0 Тогда
//         ТЗ.ВыбратьСТроку();
         ТЗ.Свернуть("СЛУЖ_КОЛ, ",СтрокаКолонок);
//         ТЗ.ВыбратьСТроку();
         Если ГдеНеверный<=ТЗ.КоличествоСтрок() Тогда
            ТЗ.УдалитьСтроку(ГдеНеверный);
         КонецЕсли;
      КонецЕсли;
      ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
      СтрокКода=26;
   ИначеЕсли Вариант="TDV" Тогда   // 19,09,02
      КонСтрока=Мин(ТЗ.НоваяКолонка("СЛУЖ_КОЛ"), 0);  // (примечание mszsuz: вот такая "оптимизация" началась, ради "красоты" ...)
      ТЗ.ВыбратьСтроки();
      Пока ТЗ.ПолучитьСтроку()=1 Цикл
         Если УсловиеВыполняется(ТЗ.К)=1 Тогда
            КонСтрока=КонСтрока+1;
            ТЗ.СЛУЖ_КОЛ=1;
         КонецЕсли;
      КонецЦикла;                      
      Если (КонСтрока=0) ИЛИ (КонСтрока=ТЗ.КоличествоСтрок()) Тогда
         ТЗ.КоличествоСтрок(КонСтрока);
         ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
      Иначе
         ТЗ.Сортировать("-СЛУЖ_КОЛ");
         ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
         ТЗ.Выгрузить(ТЗ_СЛУЖ,,КонСтрока);
         ТЗ=ТЗ_СЛУЖ;
      КонецЕсли;
      СтрокКода=17;                          
   ИначеЕсли Вариант = "alexk v.1" Тогда // ************************************ alexk v.1 18.04.03
      КолСтр = ТЗ.КоличествоСтрок();
      КолКол = ТЗ.НоваяКолонка("СЛУЖ_КОЛ");
      НачСтрока = КолСтр;
      ТЗ.ВыбратьСтроки();
      Пока ТЗ.ПолучитьСтроку() = 1 Цикл
         Если УсловиеВыполняется(ТЗ.К) = 1 Тогда
            ТЗ.СЛУЖ_КОЛ = НачСтрока;
            НачСтрока = НачСтрока - 1;
         КонецЕсли;
      КонецЦикла;
      Если НачСтрока = 0 Тогда
         ТЗ.КоличествоКолонок(КолКол-1);
      ИначеЕсли НачСтрока = КолСтр Тогда
         ТЗ.КоличествоСтрок(0); 
         ТЗ.КоличествоКолонок(КолКол-1);
      Иначе
         ТЗ.Сортировать("-СЛУЖ_КОЛ");
         ТЗ.КоличествоКолонок(КолКол-1);
         ТЗ.Выгрузить(ТЗ_СЛУЖ,,КолСтр - НачСтрока);
         ТЗ = ТЗ_СЛУЖ;
      КонецЕсли; 
      СтрокКода = 21;             
   ИначеЕсли Вариант = "alexk v.2" Тогда // ************************************ alexk v.2 18.04.03
      КолСтр = ТЗ.КоличествоСтрок();
      НачСтрока = 0;
      ТЗ.ВыбратьСтроки();
      Пока ТЗ.ПолучитьСтроку() = 1 Цикл
         Если УсловиеВыполняется(ТЗ.К) = 1 Тогда
            НачСтрока = НачСтрока + 1;
            Массив[НачСтрока] = ТЗ.НомерСтроки;
         КонецЕсли;
      КонецЦикла;
      Если НачСтрока = КолСтр Тогда
      ИначеЕсли НачСтрока = 0 Тогда
         ТЗ.КоличествоСтрок(0);
      ИначеЕсли НачСтрока = Массив[НачСтрока] Тогда
         ТЗ.КоличествоСтрок(НачСтрока);
      ИначеЕсли НачСтрока = КолСтр - Массив[1] + 1 Тогда
         ТЗ.Выгрузить(ТЗ_СЛУЖ, Массив[1]);
         ТЗ = ТЗ_СЛУЖ;
      Иначе
         Кол = ТЗ.НоваяКолонка("СЛУЖ_КОЛ");
         Для А = 1 По НачСтрока Цикл
            ТЗ.УстановитьЗначение(Массив[А], Кол, А);
         КонецЦикла;   
         ТЗ.Сортировать(Кол);
         ТЗ.КоличествоКолонок(Кол - 1);
         ТЗ.Выгрузить(ТЗ_СЛУЖ, КолСтр - НачСтрока + 1);
         ТЗ = ТЗ_СЛУЖ; 
      КонецЕсли;
      СтрокКода = 27;
   ИначеЕсли Вариант = "mech" Тогда // ************************************ mech 19,09,02   
      Нов = СоздатьОбъект("ТаблицаЗначений");
      ТЗ.НоваяКолонка("НЕУдалять","Число");
      ТЗ.ВыбратьСтроки();
      Попытка
         ~Назад:
         ТЗ.ПолучитьСтроку();
         ТЗ.НЕУдалять = УсловиеВыполняется(ТЗ.К);
         ТЗ.ПолучитьСтроку();
         ТЗ.НЕУдалять = УсловиеВыполняется(ТЗ.К);
         Перейти ~Назад;
      Исключение
      КонецПопытки;
      Итоги =  ТЗ.Итог("НеУдалять");
      КолСтрок  = ТЗ.КоличествоСтрок();
      Если Итоги = 0  Тогда
         ТЗ.УдалитьКолонку("НеУдалять");
         ТЗ.УдалитьСтроки();
      ИначеЕсли КолСтрок = Итоги Тогда
         ТЗ.УдалитьКолонку("НеУдалять");
      Иначе
         ТЗ.Сортировать("Неудалять");
         ТЗ.УдалитьКолонку("НеУдалять");
         ТЗ.Выгрузить(Нов,КолСтрок - Итоги + 1,КолСтрок);
         //Нов.Выгрузить(ТЗ);
         ТЗ = Нов;
      КонецЕсли;
      СтрокКода=25;
   ИначеЕсли Вариант="NefedovSergey" Тогда   // Nefedov Sergey 07/11/2002 Nefedov_Sergei@mail.ru
      // Высылаю свой алгоритм, на моей машине, 
      //  он показывает первое место по быстродействию
      //  отладкой особо не занимался, и так хорошо !!!
      // поправку на количесво строк текста считаю глупостью.
      сч=0;    
      Констрока=0;              
      ТЗ.ВыбратьСтроки();       
      Пока ТЗ.ПолучитьСтроку()=1 Цикл   
         сч=сч+1;
         Если УсловиеВыполняется(ТЗ.К)=0 Тогда
            КонСтрока=КонСтрока+1;
            массив[КонСтрока]=сч;
         КонецЕсли;
      КонецЦикла;                      
      Если (КонСтрока=0) ИЛИ (КонСтрока=сч)или ((сч-констрока)=(массив[1]-1)) Тогда
         ТЗ.КоличествоСтрок(сч-КонСтрока);
      ИначеЕсли констрока=массив[констрока] тогда
         ТЗ.Выгрузить(ТЗ_СЛУЖ,констрока+1,);
         ТЗ=ТЗ_СЛУЖ;
      Иначе                        
         ТЗ.НоваяКолонка("СЛУЖ_КОЛ");
         кол=ТЗ.количествоколонок();
         для а=1 по КонСтрока цикл
               ТЗ.установитьзначение(массив[а],кол,1);
         конеццикла;   
         ТЗ.Сортировать("СЛУЖ_КОЛ");
         ТЗ.УдалитьКолонку("СЛУЖ_КОЛ");
         ТЗ.Выгрузить(ТЗ_СЛУЖ,,сч-КонСтрока);
         ТЗ=ТЗ_СЛУЖ; 
      КонецЕсли;
      СтрокКода=26;                     
   ИначеЕсли Вариант="NefedovSergey /NS/" Тогда   //  Nefedov_Sergei@mail.ru   
       ВсегоСтрок=Тз.КоличествоСтрок(ТЗ.КоличествоСтрок()+2); // добавим строки вспомогательные... 
       Тз.УстановитьЗначение(ВсегоСтрок+1,"К",максЗнач); //Пропишем туда неудаляемое и удаляемое значения...   
       Тз.УстановитьЗначение(ВсегоСтрок+2,"К",0); 
       ТЗ.ВыбратьСтроки();  // найдем первую оставляемую строку 
       Пока (ТЗ.ПолучитьСтроку()=1)и(УсловиеВыполняется(ТЗ.К)=0) Цикл   
       КонецЦикла;   
       НачалоПервогоБлока=Тз.НомерСтроки; 
       Если НачалоПервогоБлока>ВсегоСтрок Тогда 
           ТЗ.УдалитьСтроки(); // Значит возвращаемую пустую ТЗ 
       Иначе   // найдем первую удаляемую строку                   
           Пока (ТЗ.ПолучитьСтроку()=1)и(УсловиеВыполняется(ТЗ.К)=1) Цикл   
           КонецЦикла; 
           КонецПервогоБлока=ТЗ.НомерСтроки; 
           Если КонецПервогоБлока>ВсегоСтрок Тогда //До самого конца дошли 
               ТЗ.УдалитьСтроку(ВсегоСтрок+2); 
               ТЗ.УдалитьСтроку(ВсегоСтрок+1); 
               Если началоПервогоБлока>1 тогда 
                   ТЗ.Выгрузить(ТЗ_СЛУЖ,НачалоПервогоБлока); 
                   ТЗ=ТЗ_СЛУЖ; 
               КонецЕсли; 
           Иначе  // найдем начало следующего блока 
               ТЗ_Служ=создатьобъект("ТаблицаЗначений"); 
               ТЗ1=создатьобъект("ТаблицаЗначений"); 
               Пока (ТЗ.ПолучитьСтроку()=1)и(УсловиеВыполняется(ТЗ.К)=0) Цикл   
               КонецЦикла; 
               НачалоОчередногоБлока=ТЗ.НомерСтроки; 
               Если НачалоОчередногоБлока>ВсегоСтрок Тогда //В таблице один блок 
                   Если началопервогоблока>1 тогда 
                       ТЗ.Выгрузить(ТЗ_СЛУЖ,НачалоПервогоБлока,КонецПервогоБлока-1); 
                   Иначе     
                       ТЗ.Выгрузить(ТЗ_СЛУЖ,1,1); 
                       ТЗ_СЛУЖ.Количествострок(КонецПервогоБлока-1); 
                       ТЗ_СЛУЖ.Заполнить(ТЗ); 
                   КонецЕсли; 
                   ТЗ=ТЗ_СЛУЖ; 
               Иначе //Метод количествоСтрок() на уменьшение не использую - он часто работает неверно. 
                   ТЗ.УдалитьСтроку(ВсегоСтрок+2); 
                   ТЗ.УдалитьСтроку(ВсегоСтрок+1); 
                   ТЗ.НоваяКолонка("_Уд"); 
                   ТЗ.Заполнить(1,НачалоПервогоБлока,КонецПервогоБлока-1,"_Уд"); 
                   ТЗ._Уд=1;   
                   колстр=конецпервогоблока-началопервогоблока+1; 
                   Пока ТЗ.Получитьстроку()=1 Цикл 
                       Если УсловиеВыполняется(ТЗ.К)=1 Тогда 
                           ТЗ._Уд=1; 
                           колстр=колстр+1; 
                       КонецЕсли; 
                   КонецЦикла;   
                   ТЗ.Сортировать("-_Уд"); 
                   ТЗ.УдалитьКолонку("_Уд");     
                   ТЗ.Выгрузить(ТЗ_СЛУЖ,1,1); 
                   ТЗ_СЛУЖ.КоличествоСтрок(колстр); 
                   ТЗ_СЛУЖ.Заполнить(ТЗ); 
                   ТЗ=ТЗ_Служ; 
               КонецЕсли; 
           КонецЕсли; 
       КонецЕсли;   
       строкКода=57; 
      
   ИначеЕсли Вариант="Simod" Тогда // mailto:bezrukov@bs.omsk.org
      ТЗ.ПолучитьСтрокуПоНомеру(1);
      п_Условие       = УсловиеВыполняется(ТЗ.К);
      п_Блок          = 1;
      ТЗ.ВыбратьСтроки();
      Пока ТЗ.ПолучитьСтроку() = 1 Цикл
         Если УсловиеВыполняется(ТЗ.К) <> п_Условие Тогда
            Если п_Блок = 3 Тогда
               ТЗ.Фильтр       = 1;
            ИначеЕсли п_Блок = 1 Тогда
               п_НачБлока      = ?(п_Условие = 0, ТЗ.НомерСтроки, 1);  //           Начало блока
               п_КонБлока      = ?(п_Условие = 0, п_НачБлока, ТЗ.НомерСтроки - 1);     // Конец блока
               п_Условие       = ?(п_Условие = 0, 1, 0);
               п_Блок          = 2;
            ИначеЕсли п_Блок = 2 Тогда
               ТЗ.НоваяКолонка("Фильтр", "Число");
               ТЗ.Заполнить(1, п_НачБлока, ?(п_Условие = 0, п_КонБлока, ТЗ.НомерСтроки - 1),"Фильтр");
               ТЗ.Фильтр       = ?(п_Условие = 0, 1, 0);
               п_Условие       = 0;
               п_Блок          = 3;
            КонецЕсли;
         КонецЕсли;
      КонецЦикла;
      Если п_Блок = 1 Тогда
         Если п_Условие = 0 Тогда
            ТЗ.УдалитьСтроки();
         КонецЕсли;
      ИначеЕсли п_Блок = 2 Тогда
         Если п_Условие = 0 Тогда
            ТЗ.КоличествоСтрок(п_КонБлока);
         Иначе
            ТЗ_П    = СоздатьОбъект("ТаблицаЗначений");
            ТЗ.Выгрузить(ТЗ_П, п_НачБлока);
            ТЗ              = ТЗ_П;
         КонецЕсли;
      ИначеЕсли п_Блок = 3 Тогда
         ТЗ_П            = СоздатьОбъект("ТаблицаЗначений");
         ТЗ.Сортировать("-Фильтр");
         п_Итог          = ТЗ.Итог("Фильтр");
         ТЗ.КоличествоКолонок(ТЗ.КоличествоКолонок() - 1);
         ТЗ.Выгрузить(ТЗ_П, 1, 1);
         ТЗ_П.КоличествоСтрок(п_Итог);
         ТЗ_П.Заполнить(ТЗ);
         ТЗ = ТЗ_П;
      КонецЕсли;
      строкКода = 45;
   Иначе            
      Предупреждение("Неизвестный вариант: "+Вариант,3);
   КонецЕсли;
   Возврат СтрокКода;
КонецФункции
//*******************************************
Процедура СформироватьНаборДанных(ТипНабора) 
   // 1 тип значение в ТЗ=Номеру строки
   // 2 тип значение в ТЗ=1 - все удовлетворяют условию
   // 3 тип значение в ТЗ=КоличествоСтрок - ни одно не удовлетворяет условию
   // 4 тип чередуются 1 и КоличествоСтрок
   Если ТипНабора=1 Тогда
      Для нс=1 по МаксЗнач Цикл
         ТЗ.ПолучитьСТрокуПоНомеру(нс);
          ТЗ.К=нс;
      КОнецЦикла;
   ИначеЕсли ТипНабора=2 Тогда
      ТЗ.Заполнить(1);
   ИначеЕсли ТипНабора=3 Тогда
      ТЗ.Заполнить(МаксЗнач);
   ИначеЕсли ТипНабора=4 Тогда
      Для нс=1 по МаксЗнач Цикл
         ТЗ.ПолучитьСТрокуПоНомеру(нс);
          ТЗ.К=?(нс%2=0,1,МаксЗнач);
      КОнецЦикла;
   ИначеЕсли ТипНабора=5 Тогда  // предложил Rom
      // нечетные позиции увеличиваются, четные уменьшаются
      К=3;
      К1=К-1;
      Рез="";
      Для НС1=2 по МаксЗнач+1 Цикл   
         ПоловинаНС=Цел(НС1/2);      
         ТЗ.УстановитьЗначение(НС1-1,"К",?(НС1%2=0,ПоловинаНС,МаксЗнач-ПоловинаНС-К1));
      КонецЦикла;
   ИначеЕсли ТипНабора=6 Тогда // противоположный 1
      Для нс=0 по МаксЗнач-1 Цикл
         ТЗ.ПолучитьСТрокуПоНомеру(нс+1);
          ТЗ.К=МаксЗнач-нс;
      КОнецЦикла;      
   КонецЕсли;                           
   // заполним балласт
   Если ТЗ.КоличествоКолонок()>1 Тогда
      Для нс=1 по ТЗ.КоличествоСтрок() Цикл
         ТЗ.УстановитьЗначение(нс,"ЧБалласт",нс);
         ТЗ.УстановитьЗначение(нс,"СБалласт",Строка(нс));
      КонецЦикла;   
   КонецЕсли;
   // ТЗ.ВыбратьСтроку();  
КонецПроцедуры
//*******************************************
Функция ТЗ_2_Стр()
   СЗЗамен=СоздатьОбъект("СписокЗначений");
   СЗЗамен.ДобавитьЗначение(" ","");
   СЗЗамен.ДобавитьЗначение("Число","Ч");
   СЗЗамен.ДобавитьЗначение("Строка","С");
   СЗЗамен.ДобавитьЗначение("""","");
   СЗЗамен.ДобавитьЗначение("{Ч,0}","X");
   СЗЗамен.ДобавитьЗначение("БАЛЛАСТ","Б");
   СЗЗамен.ДобавитьЗначение("ТаблицаЗначений","ТЗ");
   ТЗ_2_Стр=ЗначениеВСтроку(ТЗ);
   Для нсСЗЗамен=1 по СЗЗамен.РазмерСписка() Цикл  
      Заменить="";
      Искать=СЗЗамен.ПолучитьЗначение(нсСЗЗамен,Заменить);
      ТЗ_2_Стр=СтрЗаменить(ТЗ_2_Стр,Искать,Заменить);
   КонецЦикла;   
    Возврат ТЗ_2_Стр;
КонецФункции
//*******************************************
Процедура СоздатьТЗ(Балласт=0)
   ТЗ=СоздатьОбъект("ТаблицаЗначений"); 
   ТЗ.НоваяКолонка("К","Число",15,0);
   Если Балласт<>0 тогда
      ТЗ.НоваяКолонка("ЧБАЛЛАСТ","Число",15,0);
      ТЗ.НоваяКолонка("СБАЛЛАСТ","Строка",15,0);
      //ТЗ.НоваяКолонка("ДБАЛЛАСТ","Дата");
   КонецЕсли;   
   ТЗ.КоличествоСтрок(МаксЗнач); 
КонецПроцедуры   
//******************************************* 
Процедура ВсеАвторы(Ф)
   Для нс=1 по СЗВарианты.РазмерСписка() Цикл
      СЗВарианты.Пометка(нс,ф);
   КонецЦикла;   
КонецПроцедуры   
//*******************************************
Функция ПолучитьСекунды()
   Возврат _GetPerformanceCounter();
КонецФункции   
// **************************************
Процедура График_Диаграмма1(Диаграмма)
   БылПрерван=1;
   ТЗРезультаты.КоличествоСтрок(0);
   Диаграмма.Обновление(0);
   Для НомерВарианта=1 по СЗВарианты.РазмерСписка() Цикл
      Если СЗВарианты.Пометка(НомерВарианта)=0 Тогда
         Продолжить;
      КонецЕсли;   
      Автор=СокрЛП(""+СЗВарианты.ПолучитьЗначение(НомерВарианта));
      ТЗРезультаты.НоваяСтрока();
      ТЗРезультаты.Автор=Автор;
      Диаграмма.УстановитьИмяСерии(ТЗРезультаты.КоличествоСтрок(),Автор);
      сообщить("************ Вариант "+Автор,"i");
      Для НомерНабора=1 по СЗНаборыДанных.РазмерСписка() Цикл  
         Если СЗНаборыДанных.Пометка(НомерНабора)=0 тогда
            Продолжить;
         КонецЕсли;                                          
         Набор="Набор "+НомерНабора;
         Диаграмма.УстановитьИмяТочки(НомерНабора,Набор);
//         сообщить("Набор: "+ТипНабора,"i");
//         сообщить("Заполнение ... ","i");
         СоздатьТЗ(1);
         СформироватьНаборДанных(НомерНабора);
//         сообщить("Фильтр ... ","i");
         ВремяВыполненияНабора=ПолучитьСекунды();
         СтрокКода=ФильтроватьТЗ(Автор); 
//         ТЗ.ВыбратьСТроку();
         ВремяВыполненияНабора=(ПолучитьСекунды()-ВремяВыполненияНабора)*?(РасчетПроизводительности=1,СтрокКода,1);
         Диаграмма.УстановитьЗначение(НомерНабора, ТЗРезультаты.КоличествоСтрок(), ВремяВыполненияНабора,Автор+", "+Набор+": "+ВремяВыполненияНабора+?(РасчетПроизводительности=1," оч."," ед.врем."));
         ТЗРезультаты.ОбщееВремяВыполнения=ТЗРезультаты.ОбщееВремяВыполнения+ВремяВыполненияНабора;         
         сообщить(Набор+" обрабатывался: "+ВремяВыполненияНабора+?(РасчетПроизводительности=1," оч."," ед.врем."));
      КонецЦикла;             
      сообщить("************ Всего выполнялось: "+ТЗРезультаты.ОбщееВремяВыполнения+?(РасчетПроизводительности=1," оч."," ед.врем."));
   КонецЦикла;
   Диаграмма.Обновление(1);
   БылПрерван=0;
КонецПроцедуры
// **************************************
Процедура График_Диаграмма2(Диаграмма) // общий итог
   БылПрерван=1;
   Диаграмма.Обновление(0);
   ТЗРезультаты.Сортировать("-ОбщееВремяВыполнения");
   Для НомерВарианта=1 по ТЗРезультаты.КоличествоСтрок() Цикл
      ТЗРезультаты.ПолучитьСТрокуПоНомеру(НомерВарианта);
      Автор=ТЗРезультаты.Автор;
      ОбщееВремяВыполнения=ТЗРезультаты.ОбщееВремяВыполнения;
      Диаграмма.УстановитьИмяСерии(НомерВарианта,Автор);
      Диаграмма.УстановитьИмяТочки(1,"Общее время выполнения");
      Диаграмма.УстановитьЗначение(1, НомерВарианта, ОбщееВремяВыполнения,Автор+": "+ОбщееВремяВыполнения);
   КонецЦикла;
   Диаграмма.Обновление(1);
   БылПрерван=0;
КонецПроцедуры
//*******************************************
Процедура Сформировать()
   Если фОчиститьОкноСообщений=1 тогда
      ОчиститьОкноСообщений();
   КонецЕсли;   
   сообщить("Начало тестирования на "+МаксЗнач+" элементов в ТЗ ...","!");
      Т = СоздатьОбъект("Таблица");
   Т.ИсходнаяТаблица("График");
   Т.ВывестиСекцию("Диаграмма");
   Если БылПрерван=0 Тогда
      Т.ВывестиСекцию("Результаты");    
   КонецЕсли;
   Если БылПрерван=1 Тогда
      сообщить("Тестирование было прервано.","!");
       Предупреждение("Тестирование было прервано!","!");
   Иначе
      сообщить("Тестирование завершено!","!");
      Т.Опции(0, 0, 4, 0, "ОпцииПечатиДиаграмма");
      Т.ТолькоПросмотр(1);
      Т.Показать("Результаты тестирования");
   КонецЕсли;
КонецПроцедуры
//*******************************************
Процедура ПриОткрытии()
   сообщить("Проверка участников ...","i");
   МаксЗнач = 20; // проверяем на 20 элементах
   //МаксЗнач = 10; // проверяем на 10 элементах
   Для НомерНабора=1 по 6 Цикл
      СЗНаборыДанных.ДобавитьЗначение("Набор "+НомерНабора);СЗНаборыДанных.Пометка(СЗНаборыДанных.РазмерСписка(),1); 
      Если МаксЗнач = 20 Тогда
         Если НомерНабора=1 Тогда
            // "{1,2,3,4,5,6,7,8,9}";
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4},{Ч,5},{Ч,6},{Ч,7},{Ч,8},{Ч,9}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4},{Ч,5},{Ч,6},{Ч,7},{Ч,8},{Ч,9}}},{СБ,СБ,1,0,2,{С,},,0,{{С,1},{С,2},{С,3},{С,4},{С,5},{С,6},{С,7},{С,8},{С,9}}}}}}";
         ИначеЕсли  НомерНабора=2 Тогда
            // "{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}";   
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4},{Ч,5},{Ч,6},{Ч,7},{Ч,8},{Ч,9},{Ч,10},{Ч,11},{Ч,12},{Ч,13},{Ч,14},{Ч,15},{Ч,16},{Ч,17},{Ч,18},{Ч,19},{Ч,20}}},{СБ,СБ,1,0,2,{С,},,0,{{С,1},{С,2},{С,3},{С,4},{С,5},{С,6},{С,7},{С,8},{С,9},{С,10},{С,11},{С,12},{С,13},{С,14},{С,15},{С,16},{С,17},{С,18},{С,19},{С,20}}}}}}";
         ИначеЕсли  НомерНабора=3 Тогда
            // "{}";
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{}},{ЧБ,ЧБ,1,0,1,X,,2,{}},{СБ,СБ,1,0,2,{С,},,0,{}}}}}";
         ИначеЕсли  НомерНабора=4 Тогда
            // "{1,1,1,1,1,1,1,1,1,1}";
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,2},{Ч,4},{Ч,6},{Ч,8},{Ч,10},{Ч,12},{Ч,14},{Ч,16},{Ч,18},{Ч,20}}},{СБ,СБ,1,0,2,{С,},,0,{{С,2},{С,4},{С,6},{С,8},{С,10},{С,12},{С,14},{С,16},{С,18},{С,20}}}}}}";
         ИначеЕсли  НомерНабора=5 Тогда
            // "{1,2,3,4,5,6,7,8,9,9,8}";
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4},{Ч,5},{Ч,6},{Ч,7},{Ч,8},{Ч,9},{Ч,9},{Ч,8}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,1},{Ч,3},{Ч,5},{Ч,7},{Ч,9},{Ч,11},{Ч,13},{Ч,15},{Ч,17},{Ч,18},{Ч,20}}},{СБ,СБ,1,0,2,{С,},,0,{{С,1},{С,3},{С,5},{С,7},{С,9},{С,11},{С,13},{С,15},{С,17},{С,18},{С,20}}}}}}";
         ИначеЕсли  НомерНабора=6 Тогда
            // "{9,8,7,6,5,4,3,2,1}";
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,9},{Ч,8},{Ч,7},{Ч,6},{Ч,5},{Ч,4},{Ч,3},{Ч,2},{Ч,1}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,12},{Ч,13},{Ч,14},{Ч,15},{Ч,16},{Ч,17},{Ч,18},{Ч,19},{Ч,20}}},{СБ,СБ,1,0,2,{С,},,0,{{С,12},{С,13},{С,14},{С,15},{С,16},{С,17},{С,18},{С,19},{С,20}}}}}}";
         КонецЕсли;
      Иначе
         Если НомерНабора=1 Тогда
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4}}},{СБ,СБ,1,0,2,{С,},,0,{{С,1},{С,2},{С,3},{С,4}}}}}}"; // "{1,2,3,4}";
         ИначеЕсли  НомерНабора=2 Тогда
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4},{Ч,5},{Ч,6},{Ч,7},{Ч,8},{Ч,9},{Ч,10}}},{СБ,СБ,1,0,2,{С,},,0,{{С,1},{С,2},{С,3},{С,4},{С,5},{С,6},{С,7},{С,8},{С,9},{С,10}}}}}}"; // "{1,1,1,1,1,1,1,1,1,1}";   
         ИначеЕсли  НомерНабора=3 Тогда
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{}},{ЧБ,ЧБ,1,0,1,X,,2,{}},{СБ,СБ,1,0,2,{С,},,0,{}}}}}"; // "{}";   
         ИначеЕсли  НомерНабора=4 Тогда
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,1},{Ч,1},{Ч,1},{Ч,1}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,2},{Ч,4},{Ч,6},{Ч,8},{Ч,10}}},{СБ,СБ,1,0,2,{С,},,0,{{С,2},{С,4},{С,6},{С,8},{С,10}}}}}}"; // "{1,1,1,1,1}";  
         ИначеЕсли  НомерНабора=5 Тогда         
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,1},{Ч,2},{Ч,3},{Ч,4},{Ч,4},{Ч,3}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,1},{Ч,3},{Ч,5},{Ч,7},{Ч,8},{Ч,10}}},{СБ,СБ,1,0,2,{С,},,0,{{С,1},{С,3},{С,5},{С,7},{С,8},{С,10}}}}}}"; // "{1,2,3,4,4,3}";
         ИначеЕсли  НомерНабора=6 Тогда         
            Правильно="{ТЗ,2,{0,,0,0,0,,2,{{К,К,1,0,0,X,,2,{{Ч,4},{Ч,3},{Ч,2},{Ч,1}}},{ЧБ,ЧБ,1,0,1,X,,2,{{Ч,7},{Ч,8},{Ч,9},{Ч,10}}},{СБ,СБ,1,0,2,{С,},,0,{{С,7},{С,8},{С,9},{С,10}}}}}}"; // "{4,3,2,1}";
         КонецЕсли;
      КонецЕсли;
      Для НомерВарианта=1 по СЗВарианты.РазмерСписка() Цикл
         СоздатьТЗ(1); 
         СформироватьНаборДанных(НомерНабора);
         Автор=СЗВарианты.ПолучитьЗначение(НомерВарианта);
         состояние("Проверка участников на "+НомерНабора+" наборе: "+Автор);
         ФильтроватьТЗ(Автор);
         //ТЗ.ВыбратьСтроку(,""+Автор+" "+НомерНабора);
         ТоЧтоПолучилось=ТЗ_2_Стр();
         //Сообщить(ТоЧтоПолучилось);
         Если ТоЧтоПолучилось<>Правильно тогда                                                       
            сообщить("");
            сообщить("Участник "+Автор+" не правильно обрабатывает набор данных "+НомерНабора,"!!!");
            сообщить("При 20 элементах должно быть: ");
            сообщить(Правильно);
            сообщить("______________, а получилось: ");
            сообщить(ТоЧтоПолучилось); 
            СЗВарианты.Пометка(НомерВарианта,0);  
         КОнецЕсли;   
      КонецЦикла;   
   КонецЦикла;   
   сообщить("Проверка завершена.","i");
   МаксЗнач=20000; 
КонецПроцедуры
// **********************************
фОчиститьОкноСообщений=1;
ТЗ=СоздатьОбъект("ТаблицаЗначений"); ТЗ.НоваяКолонка("К","Число",15,0);

ТЗРезультаты=СоздатьОбъект("ТаблицаЗначений");
ТЗРезультаты.НоваяКолонка("Автор");
ТЗРезультаты.НоваяКолонка("ОбщееВремяВыполнения","Число",10);                         
// -->
// СЗВарианты.ДобавитьЗначение("VVS");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);       // ИСКЛЮЧЕН 15,09,2002: С ОШИБКОЙ!
// СЗВарианты.ДобавитьЗначение("Чиканук");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);  // ИСКЛЮЧЕН 15,09,2002: С ОШИБКОЙ!
// СЗВарианты.ДобавитьЗначение("Diamond");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);  // ИСКЛЮЧЕН 15,09,2002: САМЫЙ МЕДЛЕННЫЙ ИЗ РАБОТАЮЩИХ
// СЗВарианты.ДобавитьЗначение("GaninY");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);   // 20,09,2002: ИСКЛЮЧЕН КАК МЕДЛЕННЫЙ 
// СЗВарианты.ДобавитьЗначение("Rom");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);      // 20,09,2002: ИСКЛЮЧЕН КАК МЕДЛЕННЫЙ 

СЗВарианты.ДобавитьЗначение("mszsuz");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);
СЗВарианты.ДобавитьЗначение("Serpent");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);
СЗВарианты.ДобавитьЗначение("slavic");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);
СЗВарианты.ДобавитьЗначение("TDV");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);         // ДОБАВЛЕН 19,09,2002
СЗВарианты.ДобавитьЗначение("alexk v.1");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);       // ДОБАВЛЕН 19,09,2002
СЗВарианты.ДобавитьЗначение("alexk v.2");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);       // ДОБАВЛЕН 19,09,2002
СЗВарианты.ДобавитьЗначение("mech");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);        // ДОБАВЛЕН 19,09,2002 
СЗВарианты.ДобавитьЗначение("NefedovSergey");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);  // ДОБАВЛЕН 13,11,2002 
СЗВарианты.ДобавитьЗначение("NefedovSergey /NS/");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);  // ДОБАВЛЕН 05,10,2004 
СЗВарианты.ДобавитьЗначение("Simod");СЗВарианты.Пометка(СЗВарианты.РазмерСписка(),1);  // ДОБАВЛЕН 27,06,2006 
Показать полностью
8. Сергей Троицкий (tsd) 09.11.08 09:34
а не проще таблицу с конца обходить?

всего=ТЗ.Количествострок();

пока всего > 0 цикл
ТЗ.Получитьстрокупономеру(Всего);
Проверка условий ....

Всего = Всего -1;
КонецЦикла;
9. Алексей Константинов (alexk-is) 09.11.08 10:05
(8) В коде проще, но не быстрее. Самый быстрый и "правильный" из известных мне "alexk v.2"
А самый простой по коду ниже:
Код
Для Индекс = -ТЗ.КоличествоСтрок() По -1 Цикл
    ТЗ.ПолучитьСтрокуПоНомеру(-Индекс);
    Если <ПроверкаУсловий> Тогда
        ТЗ.УдалитьСтроку();
    КонецЕсли;
КонецЦикла;
Показать полностью
feniks_pro90; Бывалый77; bigmalex; leonidt84; CratosX; ya.Avoronov; wolfsoft; Fiz; +8 Ответить
10. fixin 12.11.08 21:47
Если скорость не очень важна, то можно юзать универсальную функцию из библиотеки функций.

//fixin 200707072
//Удаляет строки таблицы значений по условию
//ТЗ - таблица значений
//Код - код проверки условия, например "Р=Стр.Статья<>П"
//П - один или несколько (структура) параметров
//При проверке условия в переменную Р нужно вернуть результат (истина - удалять, ложь - не удалять),
// при этом доступна текущая строка СТР и переданный параметр Т.
Функция обУдалитьСтрокиТЗПоУсловию(ТЗ, Код, П=Неопределено) Экспорт
Всего=ТЗ.Количество();
Для Инд=1 По Всего Цикл
Поз=Всего-Инд;
Стр=ТЗ[Поз];
Р=ложь;
Выполнить(Код);
Если Р=истина Тогда
ТЗ.Удалить(Поз);
КонецЕсли;
КонецЦикла;
11. Алексей Константинов (alexk-is) 12.11.08 22:58
(12) Кроме того, что при удалении строки переписывается все последующие строки, так тут еще и компиляция "Код" в цикле.
...еще один образец того "как делать не надо"...
12. Олег Пономаренко (O-Planet) 12.11.08 23:38
(7) 0_о Это релиз для NASA метода удаления строк из таблиц?
smirnovserg.s@gmail.com; artfa; Мах; +3 Ответить 2
13. Maljaev (maljaev) 13.11.08 09:02
Вот мой вариант фильтрации ТЗ по одному или нескольким условиям. Довольно быстрый, но не самый быстрый. По крайней мере несколько лет пользуюсь только им - хватает...

Код
// процедура фильтрует таблицу в соответствии с таблицей условий
Процедура ФильтроватьТаблицу(Таблица,Условия)
   Если Таблица.КоличествоСтрок()=0 Тогда
      Возврат;
   КонецЕсли;
   КоличествоКолонок=Таблица.КоличествоКолонок();
   Результирующая=СоздатьОбъект("ТаблицаЗначений");
   Промежуточная=СоздатьОбъект("ТаблицаЗначений");
   Таблица.Выгрузить(Результирующая,1,1);
   Результирующая.КоличествоСтрок(0);
   Таблица.ВыбратьСтроки();
   Пока Таблица.ПолучитьСтроку()=1 Цикл
      СоответствуетУсловию=1;
      Условия.ВыбратьСтроки();
      Пока Условия.ПолучитьСтроку()=1 Цикл
         Значение=Условия.Значение;
         Если Шаблон("["+Условия.Шаблон+"]")="0" Тогда
            СоответствуетУсловию=0;
            Прервать;
         КонецЕсли;
      КонецЦикла;
      Если СоответствуетУсловию=1 Тогда
         Таблица.Выгрузить(Промежуточная,Таблица.НомерСтроки,Таблица.НомерСтроки);
         Результирующая.НоваяСтрока();
         Результирующая.Заполнить(Промежуточная,Результирующая.НомерСтроки,Результирующая.НомерСтроки);
      КонецЕсли;
   КонецЦикла;
   Результирующая.Выгрузить(Таблица);
КонецПроцедуры // ФильтроватьТаблицу

// функция создает и возвращает таблицу с одним значением условия
Функция ВернутьПростоеУсловие(Условие,Значение="")
   Условия=СоздатьОбъект("ТаблицаЗначений");
   Условия.НоваяКолонка("Шаблон");
   Условия.НоваяКолонка("Значение");
   Условия.НоваяСтрока();
   Условия.Шаблон=Условие;
   Условия.Значение=Значение;
   Возврат Условия;
КонецФункции // ВернутьПростоеУсловие
Показать полностью


Примеры ислользования:

Код
// очистить ТЗ от строк с нулевой суммой
ФильтроватьТаблицу(ТЗ,ВернутьПростоеУсловие("?(Таблица.Сумма=0,0,1)"));

// очистить ТЗ по заданному сотруднику, фирме, и с окладом более 5000 рублей
Условия=ВернутьПростоеУсловие("?(Таблица.Сотрудник=Значение,1,0)",ВыбСотрудник);
Условия.НоваяСтрока();
Условия.Заполнить(ВернутьПростоеУсловие("?(Таблица.Фирма=Значение,1,0)",ВыбФирма),Условия.НомерСтроки,Условия.НомерСтроки);
Условия.НоваяСтрока();
Условия.Заполнить(ВернутьПростоеУсловие("?(Таблица.Оклад>5000,1,0)"),Условия.НомерСтроки,Условия.НомерСтроки);
ФильтроватьТаблицу(ТЗ,Условия);
Показать полностью
14. Maljaev (maljaev) 13.11.08 09:09
В последнем примере комментарий неверно сформулировал. Надо читать так:
Код
// отфильтровать ТЗ по заданному сотруднику, фирме, и с окладом более 5000 рублей
Показать полностью
15. Lomok (lomok) 13.11.08 09:21
Статья стала полезной однако, после того как отцы комментов накидали :)
Плюс!
perepetulichka; +1 Ответить
16. PlatonovStepan (Jogeedae) 28.05.09 03:31
Можно фильтровать ТЗ по точному значению
//ПараметрыОтбора = новый Структура;
//ПараметрыОтбора.Вставить(сИмя,сЗнач);
//где сИмя - колонка, сЗнач - значение отбора
ТЗ = ТЗ.Скопировать(ПараметрыОтбора);
Alexey_A; zShamaNz; frost_a; rayastar; yuraskas; rhtr; mikmike; igyo; +8 Ответить
17. Сергей Алферов (SunShinne) 10.06.11 16:31
Спасибо! Очень помогло. Обычный способ в 1С действительно глючит
18. Сергей (Che) Коцюра (CheBurator) 11.06.11 01:31
какой-такой "обычный" способ..?
.я тут вчера кучу времени убил.. - две ТЗ, вроде как одинаковые даже по составу данных (колонки артикул и колво, сортируем по Артикул), сравниваю путем преобразования в строку... ан нет.. то что совершенно одинаково видится как визуальная ТЗ - при ЗначениеВстроку(ТЗ) - получается совсем не отсортированной!
19. Сергей (Che) Коцюра (CheBurator) 11.06.11 01:33
пользуюсь вот такими...
//******************************************************************************
// ОчисткаТЗ()
// Параметры: ТЗ, которую надо очистить
// В ТЗ д.б. Колонки с идентификаторами "НадоУдалить" и "ОПС" (оригинальный порядок строк)
// Описание: очищает ТЗ от ненужных строк
Процедура глОчисткаТЗ(ТЗдляЧистки, ОПС="+ОПС", КолонкаУдалить="НадоУдалить", Режим=0) Экспорт

Попытка НадоУдалить = ТЗдляЧистки.Итог(КолонкаУдалить);
Исключение Возврат;
КонецПопытки;

ТЗКС = ТЗдляЧистки.КоличествоСтрок();
Если Режим <> 0 Тогда
Сообщить("> ["+ТекущееВремя()+"]: *** удаляем "+НадоУдалить+" из "+ТЗКС+" ****");
КонецЕсли;

Если НадоУдалить <= 0 Тогда Возврат; КонецЕсли;

Если НадоУдалить >= ТЗКС Тогда
ТЗдляЧистки.УдалитьСтроки();
Иначе
ТЗРаб = СоздатьОбъект("ТаблицаЗначений");
ТЗдляЧистки.Выгрузить(ТЗРаб);
ТЗРаб.Сортировать("+"+КолонкаУдалить);
ТЗРаб.Выгрузить(ТЗдляЧистки,1,ТЗКС-НадоУдалить);
ТЗРаб = 0;
КонецЕсли;
Если ОПС = "###" Тогда Возврат; КонецЕсли; //сортировать не надо
//восстановим оригинальный порядок строк
ТЗдляЧистки.Сортировать(ОПС);
КонецПроцедуры //глОчисткаТЗ()
20. Сергей (Che) Коцюра (CheBurator) 11.06.11 01:33
//------------------------------------------------------------------------------------
Функция глОтобратьПоКолонке(ТЗВход,Колонка,Значение) Экспорт
//возвращает отобранную ТЗ
Перем ТЗ, ТЗВрем;
ТЗВход.Выгрузить(ТЗ);
ТЗ.Сортировать(Колонка+"*"); //по внутр значению
НомСтр = 0;
Если ТЗ.НайтиЗначение(Значение, НомСтр, Колонка) = 0 Тогда
//нет такого значения
ТЗ.УдалитьСтроки();
Возврат ТЗ;
Иначе
//найдем строку, в которой уже не встречается Значение
ТЗКС = ТЗ.КоличествоСтрок();
Для счСтрок = НомСтр По ТЗКС Цикл
Если ТЗ.ПолучитьЗначение(счСтрок, Колонка) <> Значение Тогда
//нужное значение есть до пред.строки
НомСтр2 = счСтрок - 1;
Прервать;
КонецЕсли;
Если счСтрок = ТЗКС Тогда
//нужное значение встречается до конца таблицы
НомСтр2 = ТЗКС;
КонецЕсли;
КонецЦикла;
КонецЕсли;
ТЗВрем = СоздатьОбъект("ТаблицаЗначений");
ТЗ.Выгрузить(ТЗВрем,НомСтр,НомСтр2); //выгрузим только строки с нужным значением
Возврат ТЗВрем;
КонецФункции //глОтобратьПоКолонке()
Parazyte; +1 Ответить
21. Сергей Гаврилов (Luck_DMST) 17.10.13 10:26
Ну а как же простое удаление?
Например, почистить список контрагентов от которых не было оплаты
НайденныеСтроки = ОплатаФакт.НайтиСтроки(Новый Структура("Сумма", 0));
Для каждого СтрокаТЧ Из НайденныеСтроки Цикл
   ОплатаФакт.Удалить(СтрокаТЧ);
КонецЦикла;
...Показать Скрыть
22. Parazyte (Parazyte) 21.10.13 22:02
(21) Luck_DMST, эт ты обознался, тут люди за семёрку гутарят.

Вообще на Мисте ИМХО наилучший вариант


А вот еще один правильный алгоритм, предложенный Wlad:

ТабЗнач.Выбратьстроки();
Пока ТабЗнач.ПолучитьСтроку()=1 Цикл
Пока (<условие>) и (ТабЗнач.НомерСтроки<>0) Цикл
ТабЗнач.УдалитьСтроку(); //следующая строка стала текущей
КонецЦикла;
КонецЦикла;

23. shard (shard) 22.10.13 00:19
(22) Parazyte, а на быстродействие проверяли?
24. Parazyte (Parazyte) 22.10.13 08:18
Нет, но это будет играть роль имхо при оооочень больших таблицах
25. Сергей Гаврилов (Luck_DMST) 22.10.13 08:19
(22) Простите, на заголовок не обратил внимания т.к. открыты были только комментарии и как раз занимался удалением строк в ТЗ
26. binx (binx) 12.10.14 19:49
(12) O-Planet,
ТЗСтроки = ТЗ.НайтиСтроки(ПараметрыОтбора);
Для каждого СтрокаУдаления Из ТЗСтроки Цикл
      ТЗ.Удалить(СтрокаУдаления);
КонецЦикла;
...Показать Скрыть

27. Cooler (Cooler) 12.10.14 20:10
28. Сергей Зенюков (Sanario) 08.04.15 13:07
29. Юрий None (FraerFFSG) 13.07.15 17:54
У меня
Для каждого Элемент из ВыборРода Цикл
НайденныеСтроки = ТЗВесьОтчет.НайтиСтроки(Новый Структура("РодВагона", ВыборРода));
Для каждого Строка Из НайденныеСтроки Цикл
   ТЗВесьОтчет.Удалить(Строка);
КонецЦикла;
КонецЦикла;

ВыборРода = Список значений
...Показать Скрыть


НЕ РАБОТАЕТ ни один ВАРИАНТ!
30. shard (shard) 14.07.15 16:17
(29) FraerFFSG, обратите внимание на 16й комментарий.
по коду - может быть надо
Для каждого Элемент из ВыборРода Цикл
НайденныеСтроки = ТЗВесьОтчет.НайтиСтроки(Новый Структура("РодВагона", Элемент));
31. Сергей Лукин (SLukin) 18.04.16 16:21

			
СтрокиПоКонтрагенту = ТЧДокумента.Скопировать();
			
Индекс = СтрокиПоКонтрагенту.Количество() - 1; 
Пока Индекс >= 0 Цикл 
	Если СтрокиПоКонтрагенту[Индекс].Договор.ТипДоговора = Перечисления.ТипыДоговоров.СПоставщиком Тогда 
		СтрокиПоКонтрагенту.Удалить(Индекс); 
	КонецЕсли; 
	Индекс = Индекс - 1; 
КонецЦикла;
...Показать Скрыть
32. Алексей Кислов (Qwest_IS) 26.04.16 17:35
33. Федор Нестеров (feka88) 24.06.16 12:30
Сделал вот так:
КолСтрок = ТаблицаПользователей.Количество();        
	СчетчикСтрок = 1;        

	Пока СчетчикСтрок < КолСтрок Цикл   	    

		СтрокаТЗ = ТаблицаПользователей.Получить(СчетчикСтрок);
		
		ПараметрыПоискаСтрок = Новый Структура;
		ПараметрыПоискаСтрок.Вставить("ИдентификаторПользователяИБ", СтрокаТЗ.ИдентификаторПользователяИБ);
		МассивСтрок = ТаблицаПользователей.НайтиСтроки(ПараметрыПоискаСтрок);
		КолОдинаковых = МассивСтрок.Количество();
		
		Если   КолОдинаковых > 1   Тогда

			ТаблицаПользователей.Удалить(СчетчикСтрок);
			КолСтрок = КолСтрок -1;  

		Иначе 
			СчетчикСтрок = СчетчикСтрок+1;
		    
		КонецЕсли; 
		
	Конеццикла;
...Показать Скрыть
34. Анна Калачева (AnnaKalacheva) 18.10.16 08:52
Мне больше всего нравится такой вариант

УдалитьТП=Новый Массив;
	Для каждого Строка из ТЗ_ТП Цикл
		Если Строка.Валюта.Код<>"974" Тогда
			УдалитьТП.Добавить(Строка);
		КонецЕсли;
	КонецЦикла;
	
	Для каждого Строка из УдалитьТП Цикл
		ТЗ_ТП.Удалить(Строка);
	КонецЦикла;
...Показать Скрыть


В массив собираем все, что нужно удалить с любыми условиями, потом удаляем. Или отбором формируем массив из элементов, которые нужно удалить.
alex-l19041; +1 Ответить
35. Анна Калачева (AnnaKalacheva) 18.10.16 09:41
Еще вариант

Сч=0;
	Пока Сч < ТЗ.Количество() Цикл
		Если ТЗ[Сч].Номер=1 Тогда
			 ТЗ.Удалить(Сч);
		 Иначе
			 Сч=Сч+1;
		 КонецЕсли;
	КонецЦикла;
...Показать Скрыть
36. Алекс Кон (alex-l19041) 18.10.16 09:57
Для написания сообщения необходимо авторизоваться
Прикрепить файл
Дополнительные параметры ответа