Точечная замена произвольных значений в текстовой строке любой длины

09.12.23

Разработка - Универсальные функции

Небольшая функция, позволяющая заменять одни строковые значения на другие внутри большого текста.

Проблема: при формировании XML-файла в каких-то тегах внутри файла стоит пустое значение (""), а нужно, чтобы там был ноль ("0").

Например, здесь это теги

ОбщКолДог, КолПровДог, ОбщКолПУДок, КолПровПУДок, ОбщКолОпер, КолПровОпер
<РезКП КодКП="НМ.ACC.07" НаимКП="Согласование проектов договоров" КолКПОтч="3" КолКПОшиб="0" КолКПНеОшиб="3" ОбщКолДог="" КолПровДог="" ОбщКолПУДок="" КолПровПУДок="" ОбщКолОпер="" КолПровОпер=""/>

А должно быть так:

<РезКП КодКП="НМ.ACC.07" НаимКП="Согласование проектов договоров" КолКПОтч="3" КолКПОшиб="0" КолКПНеОшиб="3" ОбщКолДог="0" КолПровДог="0" ОбщКолПУДок="0" КолПровПУДок="0" ОбщКолОпер="0" КолПровОпер="0"/>



Вот текст функции, которая принимает:

текст целиком;

уникальную строку, по которой можно определить начало текстового блока, внутри которого будет присходить замена;

строку-признак окончания текстового блока, в нашем случае это закрывающий тег;

строку, которую нужно найти внутри нашего текстового блока;

строку, НА которую необходимо заменить ранее в предыдущем пункте подстроки;

 

Функция ДоработатьТекстВыгружаемогоФайла(ТекстФайла, НачалоСтрокиЗамены, КонецСтрокиЗамены, ЧтоЗаменять, НаЧтоЗаменять)
	НачалоСтроки = СтрНайти(ТекстФайла, НачалоСтрокиЗамены);
	КонецСтроки =  СтрНайти(ТекстФайла,КонецСтрокиЗамены,,НачалоСтроки)+СтрДлина(КонецСтрокиЗамены);
	Строка = Сред(ТекстФайла,НачалоСтроки,КонецСтроки-НачалоСтроки+1);
	ЧастьФайлаДо = Лев(ТекстФайла,НачалоСтроки-1);
	ЧастьФайлаПосле = Прав(ТекстФайла,СтрДлина(ТекстФайла)-КонецСтроки);
	СтрокаПослеЗамены = СтрЗаменить(Строка,ЧтоЗаменять,НаЧтоЗаменять);
	Возврат ЧастьФайлаДо+СтрокаПослеЗамены+ЧастьФайлаПосле;
КонецФункции

 

Пример использования в расширяемом модуле:


&ИзменениеИКонтроль("ВыгрузитьДокумент")
Функция НМ_ВыгрузитьДокумент(УникальныйИдентификатор)

	Результат = Неопределено;

	Попытка
		УстановитьПривилегированныйРежим(Истина);

		СодержаниеВыгрузки = ЭлектронноеПредставление(УникальныйИдентификатор);

		Если СодержаниеВыгрузки = Неопределено Тогда 
			Сообщение = Новый СообщениеПользователю;
			Сообщение.Текст = НСтр("ru = 'Выгрузка данного уведомления не предусмотрена'");
			Сообщение.Сообщить();
			Возврат Неопределено;
		КонецЕсли;

		Для Каждого ЭлементВыгрузки Из СодержаниеВыгрузки Цикл

			Если Результат = Неопределено Тогда
				Результат = Новый Массив;
			КонецЕсли;

			Если ЗначениеЗаполнено(ЭлементВыгрузки.ТекстФайла) Тогда 
				ИмяВременногоФайла = ПолучитьИмяВременногоФайла();
				СохраняемыйФайл = Новый ТекстовыйДокумент;
#Вставка
				ЭлементВыгрузки.ТекстФайла = ДоработатьТекстВыгружаемогоФайла(ЭлементВыгрузки.ТекстФайла,"<РезКП КодКП=""НМ.ACC.02""","/>","=""""","=""0""");
				ЭлементВыгрузки.ТекстФайла = ДоработатьТекстВыгружаемогоФайла(ЭлементВыгрузки.ТекстФайла,"<РезКП КодКП=""НМ.ACC.03""","/>","=""""","=""0""");
				ЭлементВыгрузки.ТекстФайла = ДоработатьТекстВыгружаемогоФайла(ЭлементВыгрузки.ТекстФайла,"<РезКП КодКП=""НМ.ACC.05""","/>","=""""","=""0""");
				ЭлементВыгрузки.ТекстФайла = ДоработатьТекстВыгружаемогоФайла(ЭлементВыгрузки.ТекстФайла,"<РезКП КодКП=""НМ.ACC.06""","/>","=""""","=""0""");
				ЭлементВыгрузки.ТекстФайла = ДоработатьТекстВыгружаемогоФайла(ЭлементВыгрузки.ТекстФайла,"<РезКП КодКП=""НМ.ACC.07""","/>","=""""","=""0""");
#КонецВставки
				СохраняемыйФайл.УстановитьТекст(ЭлементВыгрузки.ТекстФайла);
				СохраняемыйФайл.Записать(ИмяВременногоФайла, ЭлементВыгрузки.КодировкаТекста);

				ФайлВыгрузки = Новый ДвоичныеДанные(ИмяВременногоФайла);
				Если УникальныйИдентификатор <> Неопределено Тогда
					СсылкаНаДвоичныеДанныеФайла = ПоместитьВоВременноеХранилище(ФайлВыгрузки, УникальныйИдентификатор);
				Иначе
					СсылкаНаДвоичныеДанныеФайла = ПоместитьВоВременноеХранилище(ФайлВыгрузки);
				КонецЕсли;

				УдалитьФайлы(ИмяВременногоФайла);

				СтруктураВыгрузки = Новый Структура;
				СтруктураВыгрузки.Вставить("АдресФайлаВыгрузки", СсылкаНаДвоичныеДанныеФайла);
				СтруктураВыгрузки.Вставить("ИмяФайлаВыгрузки", ЭлементВыгрузки.ИмяФайла);
				СтруктураВыгрузки.Вставить("ТестВыгрузки", ЭлементВыгрузки.ТекстФайла);
				СтруктураВыгрузки.Вставить("КодировкаВыгрузки", ЭлементВыгрузки.КодировкаТекста);

				Результат.Добавить(СтруктураВыгрузки);
			ИначеЕсли СодержаниеВыгрузки.Колонки.Найти("ДвоичныеДанныеФайла") <> Неопределено Тогда 
				СтруктураВыгрузки = Новый Структура;
				СтруктураВыгрузки.Вставить("АдресФайлаВыгрузки", ПоместитьВоВременноеХранилище(ЭлементВыгрузки.ДвоичныеДанныеФайла));
				СтруктураВыгрузки.Вставить("ИмяФайлаВыгрузки", ЭлементВыгрузки.ИмяФайла);
				СтруктураВыгрузки.Вставить("ТестВыгрузки", "");
				СтруктураВыгрузки.Вставить("КодировкаВыгрузки", "");

				Результат.Добавить(СтруктураВыгрузки);
			КонецЕсли;

		КонецЦикла;

		Возврат Результат;
	Исключение
		Возврат Неопределено;
	КонецПопытки;

КонецФункции

Функция ДоработатьТекстВыгружаемогоФайла(ТекстФайла, НачалоСтрокиЗамены, КонецСтрокиЗамены, ЧтоЗаменять, НаЧтоЗаменять)
	НачалоСтроки = СтрНайти(ТекстФайла, НачалоСтрокиЗамены);
	КонецСтроки =  СтрНайти(ТекстФайла,КонецСтрокиЗамены,,НачалоСтроки)+СтрДлина(КонецСтрокиЗамены);
	Строка = Сред(ТекстФайла,НачалоСтроки,КонецСтроки-НачалоСтроки+1);
	ЧастьФайлаДо = Лев(ТекстФайла,НачалоСтроки-1);
	ЧастьФайлаПосле = Прав(ТекстФайла,СтрДлина(ТекстФайла)-КонецСтроки);
	СтрокаПослеЗамены = СтрЗаменить(Строка,ЧтоЗаменять,НаЧтоЗаменять);
	Возврат ЧастьФайлаДо+СтрокаПослеЗамены+ЧастьФайлаПосле;
КонецФункции
	

 

Вступайте в нашу телеграмм-группу Инфостарт

операции со стороками

См. также

Загрузка и выгрузка в Excel Универсальные функции Программист 1С:Предприятие 8 Россия Бесплатно (free)

Описанный ниже подход позволяет в три шага заполнять формулы в Excel файлы, вне зависимости от ОС сервера (MS Windows Server или Linux). Подход подразумевает отказ от работы с COM-объектом в пользу работы через "объектную модель документа" (DOM).

30.10.2025    4155    Abysswalker    11    

46

Универсальные функции Работа с интерфейсом Программист 1С:Предприятие 8 Бесплатно (free)

Порой необходимо временно отключить расширение 1С, не удаляя его, чтобы не потерять данные. Но в этом случае при каждом запуске всем будет лезть уведомление о неактивном расширении, хотя очевидно, это техническая информация, которой не стоит лишний раз пугать пользователей.

14.05.2025    7743    DeerCven    15    

61

Универсальные функции Программист 1С:Предприятие 8 1C:Бухгалтерия Бесплатно (free)

Благодаря этим пяти строчкам можно больше не заморачиваться с загрузкой из внешних файлов. Пользуюсь везде, всегда и постоянно.

21.05.2024    52919    dimanich70    84    

174

Универсальные функции Программист 1С:Предприятие 8 1C:Бухгалтерия Абонемент ($m)

Задача: вставить картинку из буфера обмена на форму средствами платформы 1С.

1 стартмани

18.03.2024    7689    7    John_d    13    

59

Универсальные функции Программист Стажер 1С:Предприятие 8 1C:Бухгалтерия Бесплатно (free)

Пришлось помучиться с GUID-ами немного, решил поделиться опытом, мало ли кому пригодится.

12.02.2024    67426    atdonya    31    

72

Универсальные функции Программист 1С:Предприятие 8 Бесплатно (free)

На заключительных этапах, когда идет отладка или доработка интерфейса, необходимо много раз переоткрыть внешний объект. Вот один из способов автоматизации этого.

30.11.2023    9635    ke.92@mail.ru    17    

68
Комментарии
Подписаться на ответы Инфостарт бот Сортировка: Древо развёрнутое
Свернуть все
1. Xershi 1545 29.11.23 11:45 Сейчас в теме
Наверное название нужно изменить на частичную замену или в части большого текста.
Иначе зачем все это, если просто стрзаменить использовать...
starik-2005; +1 Ответить
2. starik-2005 3213 29.11.23 12:21 Сейчас в теме
(1)
стрзаменить
СтрокаХМЛ = СтрЗаменить(СтрокаХМЛ, "></", ">0</");
3. Gaffer 85 29.11.23 14:24 Сейчас в теме
(2) только эта операция заменит во всем тексте, а нужно точечно, в каком-то одном месте
4. starik-2005 3213 29.11.23 14:30 Сейчас в теме
(3)
точечно

СтрокаХМЛ = Лев(СтрокаХМЛ, Начало)
    + СтрЗаменить( Сред(СтрокаХМЛ, Начало, Коичество) ), "></", ">0</")
    + Прав(СтрокаХМЛ, Начало + Количество);
5. Gaffer 85 29.11.23 15:09 Сейчас в теме
(4) а как получить значение переменных "Начало" и "Количество", если неизвестно ни точное расположение нужного блока, ни его длина?
6. starik-2005 3213 29.11.23 15:24 Сейчас в теме
(5)
если неизвестно ни точное расположение нужного блока, ни его длина?
Особенно если этих блоков несколько, да?
ЗЫ: если нужно менять только определенные теги, и их нет в других блоках, то просто стрзаменить для этих тегов будет не хуже...
7. Gaffer 85 29.11.23 15:54 Сейчас в теме
(6) согласен, с заменой уникальных значений вполне справляется СтрЗаменить, но спозиционироваться в каком-то нужном месте текста и поменять неуникальное значение там он не сможет.
Тут либо регулярные выражения надо использовать, либо что-то вроде такой функции.
8. Xershi 1545 01.12.23 14:51 Сейчас в теме
(3) где у вас в теме публикации стоит, что нужно точечно?
В тексте есть, в теме нету...
9. BigB 193 07.12.23 22:52 Сейчас в теме
Задачу, которую описал автор решается одной командой
СтрокаХМЛ = СтрЗаменить(СтрокаХМЛ, """""", """0""");
10. Gaffer 85 09.12.23 19:38 Сейчас в теме
(9) спасибо, конечно, за подсказку, но ваш код заменит все вхождения подстроки во всем тексте)))
Для отправки сообщения требуется регистрация/авторизация