Функция сравнения значений (рекурсивно)

ChOP 226 3 8 7

Позволяет сравнивать значение с эталонным как строго (точное совпадение полей, количества и последовательности элементов массивов), так и не строго (все элементы эталона есть в значении).

Описание параметров:

Значение - сравниваемое значение. Может быть скалярным значением, а так же массивом, структурой или соответствием;

Эталон - эталонное значение, с которым будет сравниваться значение. Ожидается, что Значение будет того же типа и иметь ту же структуру, что и Эталон. Подробнее см. параметр СтрогоеСравнение;

ВызыватьИсключение - Если Истина - функция вызовет исключение с текстом описывающим на каком этапе произошла ошибка сравнения. Если Ложь - исключение вызвано не будет, а текст, описывающий ошибку сравнения функция вернёт в качестве результата. Если параметр имеет тип "Строка", то эта строка будет добавлена первой строкой к описанию ошибки сравнения если таковая произойдёт. Не обязательный. По умолчанию Ложь;

СтрогоеСравнение - общая настройка строгого сравнения. Если Истина - Значение должно полностью соответствовать Эталону. Наличие лишних полей и элементов не допускается. Порядок элементов в массиве так же важен. Если Ложь - Значение может содержать больше полей и/или элементов. Порядок элементов в массивах не важен. Главное чтобы все поля и элементы из Эталона содержались в Значении. Не обязательный. По умолчанию Ложь;

СтрогоеСравнениеМассивов - настройка строгости сравнения массивов. Имеет то же действие, что и СтрогоеСравнение, но распространяется только на массивы содержащиеся в Значении; Не обязательный. По умолчанию используются настройки заданные параметром СтрогоеСравнение;

СтрогоеСравнениеСтруктур - аналогично СтрогоеСравнениеМассивов, но действует только на структуры внутри значения;

СтрогоеСравнениеСоответствий - аналогично СтрогоеСравнениеМассивов, но действует только на соответствия внутри значения;

Возвращаемое значение

Функция возвращает Истина если Значение подходит к Эталону с учётом критериев строгого сравнения. В противном случае возвращает строку описывающую на каком этапе сравнения произошла ошибка. Если значение параметра ВызыватьИсключение равно Истина, в случае ошибки сравнения вместо возврата будет вызвано исключение с тем же текстом. Если ВызыватьИсключение имеет тип строка - текст исключения будет дополнен спереди этой строкой. Это удобно для сравнений в цикле, чтобы получать, например, номер итерации в тексте исключения и в некоторых других случаях.

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

Источник

0

См. также

ТаблицаЗначений из кроны ДереваЗначений

Преобразование Объекта ДеревоЗначений в Объект ТаблицаЗначений

СкопироватьРекурсивно (БСП)

Сравнить ТЗ

ЗначениеТипаИспользованиеГруппИЭлементов (БСП)

ЗначениеТипаГруппыИЭлементы (БСП)

Сравнение двух массивов

Модератору