Эмуляция ООП в 1С8

14.03.12

Разработка - Рефакторинг и качество кода

Скорее экспериментально-теоретическое, чем практическое руководство по использованию ООП В 1С8.

Скачать исходный код

Наименование Файл Версия Размер
down.zip
.zip 15,93Kb
8
.zip 15,93Kb 8 Скачать

К великому нашему прискорбию в 1С 8.0 не включено объектно-ориентированное программирование. Не будем обсуждать в данной статье почему разработчики решили обойтись без него.

В семерке тоже не было ООП. Некоторые умельцы реализовывали ООП с помощью внешних обработок. Мы пойдем другим путем – документированным.

Как говорится, если нельзя, но очень хочется, то можно.

Вы увидите, что основная парадигма ООП реализуется штатными средствами 1С 8.0.

Что такое объект в понятиях ООП?

Объект состоит из свойств и методов.

Объект может наследовать методы и свойства от другого объекта – предка.

Реализация в 1С 8

Для моделирования свойств объектов прекрасно подойдет объект типа «Структура», где можно хранить любые свойства любого типа.

Для реализации методов объектов будем использовать общие модули, по одному на каждый объект. В этих модулях будем описывать методы объекта в виде функций с именами ТипОбъекта_ИмяМетода. Хотелось бы конечно писать просто ОбмяМетода(Параметры), но придется писать примерно вот так: Метод(Об, ИмяМетода, Параметры).

Для передачи параметров опять же будем использовать только один параметр типа структура, который может содержать в себе любое количество параметров. К сожалению 1С не поддерживает вызов процедур с произвольным количеством и порядком вызова параметров.

Каждый объект содержит по ключу «Тип» название своего типа, для вызова соответствующего метода используется документированная функция «Выполнить».

Если метод не найден у объекта, он ищется у предка. Тип предка определяется через вызов у объекта метода Предок, если метод определен.

Если вызываемый метод не определен, система ничего не делает.

В методе можно вызвать метод предка, примерно так Предок(Об, ИмяМетода, Параметры).

Свойства можно назначать непосредственно, но для обеспечения контроля над свойствами лучше использовать функции Установить(Об, Свойство, Зн) и Получить(Об, Свойство).

Можно написать перехватчики событий установки-чтения свойств. Они носят имя ТипОбъектастановить и ТипОбъекта_Получить. Если ТипОбъектастановить возвращает истину, то свойство устанавливается, если ложь, то нет (этот обработчик может уже установить значения свойства и повторно его ставить не надо или запретить изменение свойства).

Конструктор объекта описывается в функции ТипОбъектаоздать.

Деструктор объекта описывается в функции ТипОбъектадалить. К сожалению, все вызовы деструкторов нужно вызывать явно, т.к. в 1С 8.0 нельзя отследить момент удаления локальной переменной.

Таким образом для реализации ООП достаточно 6 функций:

·         Создать

·         Метод

·         Предок

·         Установить

·         Получить

·         Удалить

Невероятно, но факт.

В принципе, объекты 1С 8.0 (документы, справочники и т.п.) можно рассматривать уже как готовые объекты. Действительно, у них можно получить тип. Кроме того, они обладают набором свойств. Таким образом, можно унифицировать работу с объектами через вышеуказанные шесть методов.

И если завтра вместо документа вы решите использовать справочник возможно в коде, ничего не придется менять.

Резюме.

Как я показал, ООП в 1С 8.0 можно реализовать легко и красиво, добавив только6 функций.

Зачем это нужно?

Некоторые библиотеки функций удобнее реализовать в виде библиотеки классов.

Например, списание по партиям удобно реализовать в виде объекта ОчередьПартий, а каждое из списаний по товарам, по долгам будет наследовать от базовой очереди, внося новые свойства.

Также можно реализовать библиотеки для работы с файлами, строками и т.п.

Единственно, нужно учитывать, что объектно-ориентированный подход в нашем случае нужно применять там, где прозрачность и понятность разработки важнее быстродействия, т.к. методы интерпретатора Выполнить все же медленнее скомпилированного кода 1С.

И все же, если в очередном релизе появится метод ВыполнитьФункцию(Имя Функции, Параметры), все ограничения по скорости будут сняты и ООП восторжествует. Видите, как для этого мало надо!

Кроме того, если использовать функцию Шаблон и вместо Структуры Список значений, то подобное ООП можно реализовать и в 7.7, правда вся реализация методов должна быть в одном глобальном модуле (в семерке нельзя реализовать несколько модулей).

Ну конечно бы хотелось, чтобы для всех 6 методов были введены операторы, но это уже от лукавого. Аминь!

 

Приложение.

Здесь я порекомендую разработчикам 1С 8.0 операторы для функций.

 

Создать = СоздатьОбъект ТипОбъекта

Метод = Об.Метод(Параметры)

Предок = Об::Метод(Параметры)

Установить = Об.Свойство=Зн;

Получить = Об.Свойство=Получить;

Удалить = УдалитьОбъект Об.

//Реализация объекта 1

Функция Объект1_Создать(Прм="")

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

Функция Объект1_Печать(Я, Прм="")

Сообщить("Я объект 1");

Возврат 1;

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

 

Функция Объект1_Известить(Я, Прм="")

Сообщить(Получить(Я, "Информация"));

Возврат 1;

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

 

 

//Реализация объекта 2

Функция Объект2_Создать(Прм="")

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

 

Функция Объект2_Предок(Я, Прм="")

Возврат "Объект1";

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

 

Функция Объект2_Известить(Я, Прм="")

Сообщить("1С 8.0 - объектно-ориентированная среда!!! "+Прм);

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

 

 

//Реализация объекта 3

Функция Объект3_Создать(Прм="")

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

 

Функция Объект3_Предок(Я, Прм="")

Возврат "Объект2";

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

 

Функция Объект3_Печать(Я, Прм="")

Сообщить("Я объект 3");

Предок(Я, "Известить", "Верите?");

Возврат 3;

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

 

 

//// ФУНКЦИИ, РЕАЛИЗУЮЩИЕ ООП В 1С 8.0 /////

 

//Вызывает функцию, определенную в предке

Функция Предок(Об, Метод, Прм="", Сработал=ложь)

Перем Результат, Тип, Предок;

 

//Получаем тип объекта

Тип=Об.Тип;

 

Сработал=истина;

Попытка

Предок=Вычислить(Тип+"_Предок(Об, Прм)");

Попытка

Результат=Вычислить(Предок+"_"+Метод+"(Об, Прм)");

Возврат Результат;

Исключение

КонецПопытки;

Исключение

КонецПопытки;

Сработал=ложь;

Возврат Неопределено;

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

 

Функция Метод(Об, Метод, Прм="", Сработал=ложь)

Перем Тип;

 

Сработал=истина;

 

//Получаем тип объекта

Тип=Об.Тип;

 

//Сначала пробуем просто вызвать метод самого объекта

Попытка

Возврат Вычислить(Тип+"_"+Метод+"(Об, Прм)");

Исключение

КонецПопытки;

 

Сработал=ложь;

//Затем пробуем вызвать метод у предка объекта

Возврат Предок(Об, Метод, Прм);

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

 

 

//Создает объект

Функция Создать(Тип, Прм="")

Об=Новый Структура;

Об.Вставить("Тип",Тип);

Метод(Об, "Создать", Прм);

Возврат Об;

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

 

Функция Установить(Об, Свойство, Зн)

Перем Сработал, Рез;

Прм=Новый Структура;

Прм.Вставить("Свойство", Свойство);

Прм.Вставить("Значение", Зн);

Рез=Метод(Об, "Установить", Прм, Сработал);

Если (Не Сработал) ИЛИ (Рез=Истина) Тогда

Об.Вставить(Свойство, Зн);

КонецЕсли;

Возврат Зн;

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

 

Функция Получить(Об, Свойство)

Перем Сработал, Зн;

Прм=Новый Структура;

Прм.Вставить("Свойство", Свойство);

Зн=Метод(Об, "Получить", Прм, Сработал);

Если Не Сработал Тогда

Если Не Об.Свойство(Свойство, Зн) Тогда

Зн=Неопределено;

КонецЕсли;

КонецЕсли;

Возврат Зн;

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

 

 

Процедура Сформировать(Элемент)

// Вставить содержимое обработчика.

Об1=Создать("Объект1");

Об2=Создать("Объект2");

Об3=Создать("Объект3");

Рез1=Метод(Об1, "Печать");

Рез2=Метод(Об2, "Печать");

Рез3=Метод(Об3, "Печать");

Сообщить("Результаты: "+Рез1+" "+Рез2+" "+Рез3);

Сообщить("Сначала информации нет:"+Получить(Об1, "Информация"));

Установить(Об1, "Информация", "Я храню некую информацию");

Сообщить("Потом мы ее устанавливаем:"+Получить(Об1, "Информация"));

КонецПроцедуры

 

См. также

Результаты ревью кода 1500+ решений каталога Инфостарт: наиболее частые ошибки разработчиков в коде

Рефакторинг и качество кода Платформа 1С v8.3 Бесплатно (free)

Поделюсь своим опытом аудита кода авторских продуктов с Infostart.ru как одним из элементов применения DevOps-практик внутри Инфостарт. Будет настоящий код, боевые скриншоты, внутренние мемы от команды ИТ-лаборатории Инфостарт и прочее мясо – все, что любят разработчики.

10.04.2024    4757    artbear    70    

70

Ниндзя-код

Рефакторинг и качество кода Платформа 1С v8.3 Россия Бесплатно (free)

Предлагаю вашему вниманию советы мастеров древности. Программисты прошлого использовали их, чтобы заострить разум тех, кто после них будет поддерживать код. Гуру разработки при найме старательно ищут их применение в тестовых заданиях. Новички иногда используют их ещё лучше, чем матёрые ниндзя. Прочитайте их и решите, кто вы: ниндзя, новичок или, может быть, гуру? (Адаптация статьи "Ниндзя-код" из учебника JavaScript)

01.04.2024    2244    DrAku1a    15    

33

Практическое программирование: когда скорость важнее совершенства

Рефакторинг и качество кода Бесплатно (free)

В новом материале мы анализируем, как в программировании баланс между быстротой разработки и тщательной проработкой кода влияет на конечный продукт. Обсуждаем, почему иногда важнее сосредоточиться на скорости выполнения проекта, и когда можно позволить себе уступить в качестве ради достижения бизнес-целей.

01.04.2024    580    Prepod2003    6    

2

Когда понадобился новый оператор

Рефакторинг и качество кода Платформа 1С v8.3 Конфигурации 1cv8 Бесплатно (free)

Когда понадобился новый оператор, но его нет в синтакс-помощнике, что делать?

18.03.2024    1339    ZhokhovM    4    

4

Когда разработчик платформы не добавил проверку препроцессоров

Рефакторинг и качество кода Платформа 1С v8.3 Конфигурации 1cv8 Бесплатно (free)

Когда разработчик платформы решил пойти на кухню за кофе, а проверку препроцессоров не добавил, и вот тут-то и началось: "Что, опять все сломалось? Ну и кофе же я забыл сделать!".😅

18.03.2024    2976    ZhokhovM    4    

9

Реструктуризация - бесконечная история

Рефакторинг и качество кода Платформа 1С v8.3 Бесплатно (free)

При разработке программ требуемый функционал ставят на первое место, но есть еще и архитектура программы. На горизонте 5-10 лет она становится важнее функционала, который должен работать при масштабировании и росте данных. Реструктуризация 5 терабайтной базы 1С 8.2 в формат 1С 8.3, складывает весь пазл архитектурных просчетов, которые сделали ради функционала. Как это исправить? - для разработки правильной архитектуры, нужно всего лишь сместить фокус с функционала и подумать о «вечном».

29.09.2023    2059    1CUnlimited    15    

23
Комментарии
Подписаться на ответы Сортировка: Древо развёрнутое
Свернуть все
1. itar59 87 14.03.12 11:26 Сейчас в теме
Спасибо! Очень поучительно!
2. saiten 246 14.03.12 14:07 Сейчас в теме
Я подумал было, что и впрямь объектно-ориентированный подход к эске кто придумал... :)
3. aim 14.03.12 15:38 Сейчас в теме
ООП создавалось не ради классов, наследований, перегрузки, конструкторов/деструкторов. Нет, -- оно ставило задачи повторного использования кода и улучшения читаемости/сопровождаемости миллион-строчных программ. В те же годы предпринимались усилия для анализа и структурирования кода программ (открытые-закрытые члены, модель документ-представление и т.д). Криво спроектированная система классов (ООП) способна действовать в направлении, обратном вышесказанному. Хотя возможно будет радовать создателя -- "могу же! ведь ООП же!"
RomanRomans; item; +2 Ответить
4. SiAl 76 14.03.12 23:04 Сейчас в теме
А для чего? Стандартных классов, типа справочники, документы, перечисления - не хватает?
5. Magister 134 15.03.12 02:02 Сейчас в теме
(4) Автор хороший пример привел - списание по партиям.
Вспомните, неужели у вас не было случаев, когда похожие (но таки разные!) алгоритмы использовались в разных местах? Да, можно это совместить в одну процедуру, которая будет менять своё поведение в зависимости от переданных параметров. Но намного удобнее сделать один класс со "стандартным" поведением, и несколько производных, с частично измененным.
7. SiAl 76 16.03.12 15:02 Сейчас в теме
(5) намного удобнее? ИМХО: вряд ли. Создание сущностей без их явной необходимости.
(6) Методы чего? Чтение через OLE и ADO отличаются и немало.
8. fixin 4253 16.03.12 17:21 Сейчас в теме
(7) отличаются в инициализации, но не в доступе к ячейке i,j
9. Magister 134 17.03.12 14:25 Сейчас в теме
(7) Вопрос в том, насколько широкой должна быть возможность изменения поведения.
Целесообразность должна определяться конкретной задачей, нет "серебрянной пули" на все случаи.
(0)
Единственно, нужно учитывать, что объектно-ориентированный подход в нашем случае нужно применять там, где прозрачность и понятность разработки важнее быстродействия, т.к. методы интерпретатора Выполнить все же медленнее скомпилированного кода 1С.

Не факт. Я не знаю внутренностей метода "Выполнить", но следуя здравой логике - замедление не должно быть сколько-нибудь заметным. Ведь сам код находится внутри функции вызываемого метода, и никто не мешает выполнять его скомпилированным. Замедление будет только на этапе самого вызова функции, и то не факт.
Другое дело если передавать в "Выполнить" не имя функции, а сам программный текст - тогда да, замедление будет.
6. fixin 4253 15.03.12 05:56 Сейчас в теме
(4) например, задача чтения из Эксель. Можно читать через OLE-объект, через ADO, через свои ВК. Но методы остаются одинаковыми.
10. BorisMor 310 20.03.12 21:11 Сейчас в теме
Плюс за то что заставляет 1С-программистов задумываться о том чего не хватает.
Лично мне ООП не хватает больше всего. Хоть и есть в 1С различные модули, но структурирование логики программы дается с большим трудом. А большинство вообще не забивают голову и превращают программы на 1С в мешанину функций и процедур.
11. krv2k 375 30.03.12 18:50 Сейчас в теме
12. aim 04.04.12 16:31 Сейчас в теме
какие-то классы надуманные.
Я бы начал с того, что создал класс, например, "счет10", -- который умеет приходовать на этот счет, и списывать с него (при списании умееет посчитать остатки). Если надо -- сделает это в налоговом плане счетов, если надо в бухгалтерском.
"Выше" идет класс "проводка10_60", который соединит "счет10" и "счет60"(умеет считать авансы). При создании (в конструкторе) они обменяются настроечной информацией (все ли поля заполнены и т.д.). Есть "проводкаНДС", котороый считает НДС.
Ещё "выше" -- класс "документ" и.д. В принципе, класс "документ_ручная_проводка" должен быть базовым для всех "документов", но может вызываться самостоятельно.
Что-то из вышесказанного можно реализовать через "модуль менеджера".
13. fixin 4253 04.04.12 17:58 Сейчас в теме
(12) вы бредите. есть объект счет, он более универсальный чем счет 10 и счет 60.
14. aim 05.04.12 07:46 Сейчас в теме
Я что-то писал об "универсальности"?
О каком-таком "универсальном объекте счет" идет речть? Оба объекта "счет10" и "счет60" придумал пока я :)
15. aim 05.04.12 08:00 Сейчас в теме
"бредите..."
Не надо сильных слов, тем более при создании чего-то нового, неизведанного; тем более при "мозговом штурме".
Оставьте свое сообщение