<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
<channel>
	<title>Хабрахабр / Комментарии к посту «Проектирование по контракту» в блоге «Ненормальное программирование»</title>
	<link>http://habrahabr.ru/rss/post/38612/</link>
	<description><![CDATA[Новые комментарии к посту «Проектирование по контракту» в блоге «Ненормальное программирование»]]></description>
	<language>ru</language>
	<managingEditor>editor@habrahabr.ru</managingEditor>
	<generator>habrahabr.ru</generator>
	<pubDate>Sat, 11 Feb 2012 14:15:24 GMT</pubDate>
	<lastBuildDate></lastBuildDate>
	<image>
		<link>http://habrahabr.ru/</link>
		<url>http://habrahabr.ru/i/logo.gif</url>
		<title>Хабрахабр</title>
	</image>
	

	
	
	
	
	
		
	
		<item>
			<title>05.09.2008 06:57:32 Blackened</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_930496</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_930496</link>
			<description><![CDATA[&gt;Если же имеем обрывы связи, файлы с оибками и т.п — то надо заранее это все обрабатывать и куда-то делать эти предпроверки… Эхх если бы среда програмирования сама прятала бы эти проверки<br/>
<br/>
Ну тут и предпроверки, и постпроверки (формат ввода, CRC и прочее). Их можно спрятать в адаптеры, взаимодействующие с внешним миром с одной стороны, а с другой выдающие вызывающей программе результат уже по контракту. Конечно, было бы хорошо, если бы всё это делала среда, но только везде нужно реагировать на конкретные неточности извне по-своему.<br/>
<br/>
&gt; Были бы они в Debug mode в виде assert-ов, но показывались только по желанию.<br/>
<br/>
assert-ы к внешнему миру не применимы, т.к. они помогают удостовериться, что всё идёт так, как предполагает разработчик, а предположения относительно внешнего мира делать трудно.]]></description>
			<pubDate>Fri, 05 Sep 2008 06:57:32 GMT</pubDate>
			<author>Blackened</author>
		</item>
	

	
		<item>
			<title>04.09.2008 19:30:50 cdev</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_929551</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_929551</link>
			<description><![CDATA[&gt; DBC говорит о том, что если перед вызовом ситуация удовлетворяет предусловию функции, то она выполнится без ошибок <br/>
<br/>
К сожалению это так только если не взаимодействовать с внешним миром.<br/>
Если же имеем обрывы связи, файлы с оибками и т.п — то надо заранее это все обрабатывать и куда-то делать эти предпроверки. Возможно в функции типа bool ВсеOK?(окружение).<br/>
<br/>
Эхх если бы среда програмирования сама прятала бы эти проверки — то мороки бы и не было. Были бы они в Debug mode в виде assert-ов, но показывались только по желанию. Чтобы красиво было :)]]></description>
			<pubDate>Thu, 04 Sep 2008 19:30:50 GMT</pubDate>
			<author>cdev</author>
		</item>
	

	
		<item>
			<title>03.09.2008 02:52:46 eugenius_nsk</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_923022</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_923022</link>
			<description><![CDATA[Вот статья об этом паттерне — <a href="http://ru.smalltalk.wikia.com/wiki/%D0%9E%D0%B1%D0%BE%D0%B1%D1%89%D0%B5%D0%BD%D0%BD%D1%8B%D0%B9_%D0%BF%D0%B0%D1%82%D1%82%D0%B5%D1%80%D0%BD_%22Null_Object%22">http://ru.smalltalk.wikia.com/wiki/Обобщенный_паттерн_«Null_Object»</a>.]]></description>
			<pubDate>Wed, 03 Sep 2008 02:52:46 GMT</pubDate>
			<author>eugenius_nsk</author>
		</item>
	

	
		<item>
			<title>02.09.2008 17:34:26 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_921395</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_921395</link>
			<description><![CDATA[Почему не переносим? Очень даже, проверено опытом. ;)<br/>
Как правильно было сказано — переносим со своими контрактами (важна документация данных контрактов). Кроме того, переносимость наоборот облегчается за счет снижения связанности модулей.<br/>
А уж использовать такой модуль или нет (со всеми контрактами) — решать клиенту. См. мой комментарий про пирожки ;)]]></description>
			<pubDate>Tue, 02 Sep 2008 17:34:26 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 17:12:18 Blackened</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_921340</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_921340</link>
			<description><![CDATA[Переносим, но только вместе со своими контрактами]]></description>
			<pubDate>Tue, 02 Sep 2008 17:12:18 GMT</pubDate>
			<author>Blackened</author>
		</item>
	

	
		<item>
			<title>02.09.2008 16:31:53 iliich</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_921213</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_921213</link>
			<description><![CDATA[Мног интересного, для размышления. Насколько понимаю, такой код по сути не переносим в другие проекты? Тогда польза такого кода в его компактности?]]></description>
			<pubDate>Tue, 02 Sep 2008 16:31:53 GMT</pubDate>
			<author>iliich</author>
		</item>
	

	
		<item>
			<title>02.09.2008 15:33:02 mraleph</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_921011</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_921011</link>
			<description><![CDATA[<blockquote>Постусловия выражают состояния «окружающего мира» на момент выполнения подпрограммы. </blockquote><br/>
Мне кажется лучше сказать на момент завершения подпрограммы.<br/>
<br/>
<blockquote>Кроме того, наличие постусловия в подпрограмме гарантирует ее завершение (т.е. не будет бесконечного цикла, например).</blockquote><br/>
<br/>
Интересно, что в классической логике Хоара наличие постусловия никак не связано собственно с её завершением. Формулируется два понятия:<br/>
<br/>
Программа с предусловие P и постусловием Q корректна, если начиная работать на входных данных удовлетворяющих P, она либо не завершается, либо завершается в состоянии удовлетворяющем Q.<br/>
<br/>
Программа с предусловие P и постусловием Q <b>тотально</b> корректна, если начиная работать на входных данных удовлетворяющих P она завершается в состоянии удовлетворяющем Q.<br/>
<br/>
Вообще завершение или не завершение программы больше зависит от предусловия, чем от постусловия. <br/>
]]></description>
			<pubDate>Tue, 02 Sep 2008 15:33:02 GMT</pubDate>
			<author>mraleph</author>
		</item>
	

	
		<item>
			<title>02.09.2008 14:44:09 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920877</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920877</link>
			<description><![CDATA[так я об этом и писал чуть выше. возможны вызовы различными клиентами, соответственно, возможны и различные поведения в случае ошибки. Или вы предлагаете создать несколько типов объектов-исключений для описанного выше примера?<br/>
Кроме того, г-н <a href="http://blackened.habrahabr.ru/">Blackened</a> написал хорошее замечание чуть выше.]]></description>
			<pubDate>Tue, 02 Sep 2008 14:44:09 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 14:39:02 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920863</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920863</link>
			<description><![CDATA[спасибо. поправил]]></description>
			<pubDate>Tue, 02 Sep 2008 14:39:02 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 14:20:11 dendron</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920829</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920829</link>
			<description><![CDATA[А если функция вызывается много раз на разных данных? Обрамлять её каждый раз проверками утомительно, а обработку исключений можно написать в один блок после вызовов.]]></description>
			<pubDate>Tue, 02 Sep 2008 14:20:11 GMT</pubDate>
			<author>dendron</author>
		</item>
	

	
		<item>
			<title>02.09.2008 14:19:55 altspam</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920828</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920828</link>
			<description><![CDATA[Первый пример «качественного ПО» пропустит код длиной более 9 символов.]]></description>
			<pubDate>Tue, 02 Sep 2008 14:19:55 GMT</pubDate>
			<author>altspam</author>
		</item>
	

	
		<item>
			<title>02.09.2008 13:30:44 Blackened</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920692</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920692</link>
			<description><![CDATA[Тем, что нужно исключение(я) ловить и обрабатывать. DBC говорит о том, что если перед вызовом ситуация удовлетворяет предусловию функции, то она выполнится без ошибок и ничего обрабатывать не придётся. И перед вызовом проверять ничего не нужно, т.к. убедиться в выполнении предусловия можно исходя из постусловий и инвариантов предшествующих вызовов. Проверять нужно только внешние данные, от которых нельзя ждать выполнения каких-либо контрактов.]]></description>
			<pubDate>Tue, 02 Sep 2008 13:30:44 GMT</pubDate>
			<author>Blackened</author>
		</item>
	

	
		<item>
			<title>02.09.2008 13:13:43 Yanis</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920649</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920649</link>
			<description><![CDATA[&gt; Центральными фигурами это концепции<br/>
Скорее всего, имело ввиду: «Центральными фигурами это<u>Й</u> концепции».]]></description>
			<pubDate>Tue, 02 Sep 2008 13:13:43 GMT</pubDate>
			<author>Yanis</author>
		</item>
	

	
		<item>
			<title>02.09.2008 11:57:44 dendron</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_920388</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_920388</link>
			<description><![CDATA[Но ведь вызванная функция может сгенерировать исключение, а вызывающая — обработать его как хочет, чем это плохо?]]></description>
			<pubDate>Tue, 02 Sep 2008 11:57:44 GMT</pubDate>
			<author>dendron</author>
		</item>
	

	
		<item>
			<title>02.09.2008 08:55:54 svetko</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919829</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919829</link>
			<description><![CDATA[побольшье бы примеров применения и их прреимущества!]]></description>
			<pubDate>Tue, 02 Sep 2008 08:55:54 GMT</pubDate>
			<author>svetko</author>
		</item>
	

	
		<item>
			<title>02.09.2008 08:46:01 thebird</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919790</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919790</link>
			<description><![CDATA[интересная методика. Местами согласен.<br/>
Но не для русских программистов. Мозг построен немного не так =)]]></description>
			<pubDate>Tue, 02 Sep 2008 08:46:01 GMT</pubDate>
			<author>thebird</author>
		</item>
	

	
		<item>
			<title>02.09.2008 08:10:13 stab</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919628</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919628</link>
			<description><![CDATA[На счёт проверок на null, попадалась мне на глаза с полгода назад любопытная «бумага», описывался в ней способ статической проверки на основе уже имеющейся информации об исключениях в существующем C#/CIL коде. Вывод был такой: если в программе обработка и кидание исключений сделаны правильно, надобность в пред/пост условиях не столь велика. Хотя, для отделения мух от котлет, конечно лучше иметь в арсенале и исключения и весь спектр средств контрактного программирования.<br/>
<br/>
Радует, что программирование наконец-то переходит на семантический уровень, только и «мозг» компиляторма надо будет иметь соответсвующий. Отчего-то вспоминается проблема останова ;)]]></description>
			<pubDate>Tue, 02 Sep 2008 08:10:13 GMT</pubDate>
			<author>stab</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:50:20 tenshi</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919565</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919565</link>
			<description><![CDATA[окном ошибся =)<br/>
<br/>
это не контракт, а доверенность. а когда все друг-другу доверяют — невыполнение контракта одним звеном приводит к падению другого и танцам с бубном вокруг отладчика<br/>
<br/>
а вот контракт выглядит так: каждый объект обязуется реализовать некоторый интерфейс (подписывает контракт) и за выполнением контрактов следит специальный объект-аудитор (обычно его роль возлагается на интерпретатор, что сильно уменьшает гибкость). соответственно на продакшене и на тестинге могут быть разные аудиторы — разной степени скрупулёзности и с разными последствиями в случае нарушения контракта.]]></description>
			<pubDate>Tue, 02 Sep 2008 07:50:20 GMT</pubDate>
			<author>tenshi</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:42:25 mihcom</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919542</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919542</link>
			<description><![CDATA[<blockquote>Вот мой совет для данной ситуации – если вы вызываете подпрограмму, которая была написана вами, то не пишите лишнего кода. Доверяйте себе.</blockquote><br/>
<br/>
Не согласен. Поступая таким образом, вы устанавливаете неявные условия, необходимые для корректной работы программы, и если они будут нарушены (кто-то или вы сами случайно передадите неверные исходные данные), то программа поведёт себя непредсказуемо. Я считаю, что нужно избегать таких неявных зависимостей, так как это грозит неприятностями в будущем.]]></description>
			<pubDate>Tue, 02 Sep 2008 07:42:25 GMT</pubDate>
			<author>mihcom</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:39:57 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919533</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919533</link>
			<description><![CDATA[&gt;Кроме того контрактное программирование без документации, имхо, это смерть.<br/>
вот это самое главное замечание, которое я, к своему стыду, забыл упомянуть.]]></description>
			<pubDate>Tue, 02 Sep 2008 07:39:57 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:36:18 tenshi</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919519</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919519</link>
			<description><![CDATA[(for var i = 0; i &lt; links.length; i++) {<br/>
(function(i) {<br/>
links[i].onclick = function() {<br/>
alert(i);<br/>
}<br/>
})(i);<br/>
}]]></description>
			<pubDate>Tue, 02 Sep 2008 07:36:18 GMT</pubDate>
			<author>tenshi</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:35:41 justonce</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919518</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919518</link>
			<description><![CDATA[Ну, даже банальная проверка на null может сэкономить некоторое количество нейронов. Кроме того контрактное программирование без документации, имхо, это смерть. Спасает только читабельная сигнатура метода типа <br/>
<br/>
string ToPhysicalPath(string notNullVirtualPathWithSlashesAsSeparatorsAndNoEndingSlash) :)<br/>
<br/>
Spec# же включает хоть какое нибудь описание контракта в сигнатуру метода, которая потом в IntelliSense отображается]]></description>
			<pubDate>Tue, 02 Sep 2008 07:35:41 GMT</pubDate>
			<author>justonce</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:34:22 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919514</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919514</link>
			<description><![CDATA[согласен, появляется соблазн сделать проверку внутри подпрограммы. Приведу классический пример с функцией вычисления квадратного корня (назовем ее CalcSqrt(), т.е. это будет наша функция (абстрагируясь от реализации для различных языков)).<br/>
Данная функция имеет предусловие — ее аргумент не должен быть отрицательным. Если, к примеру, пользователь вводит отрицательное, то это забота вызывающей программы проверить это число. <br/>
Одна вызывающая программа завершит работу аварийно, другая выдаст предупреждение и заставит пользователя вводить еще раз значение. А третья программа вообще схитрит — она сделает это число положительным, а потом, когда получит результат, то прибавит мнимую единицу.<br/>
Поэтому, это не забота функции CalcSqrt() обрабатывать предусловия.]]></description>
			<pubDate>Tue, 02 Sep 2008 07:34:22 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:16:26 Bygaga</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919450</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919450</link>
			<description><![CDATA[Когда ожидать продолжения?]]></description>
			<pubDate>Tue, 02 Sep 2008 07:16:26 GMT</pubDate>
			<author>Bygaga</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:14:21 SlashDev</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919443</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919443</link>
			<description><![CDATA[Весьма интересный подход. Записываюсь в ряды ожидающих продолжения.]]></description>
			<pubDate>Tue, 02 Sep 2008 07:14:21 GMT</pubDate>
			<author>SlashDev</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:13:44 stab</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919442</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919442</link>
			<description><![CDATA[Пытается, только что он будет делать когда я потребую в контракте передачу функции только n-битного простого числа, и передам например такое:<br/>
<br/>
25195908475657893494027183240048398571429282126204032027777137836043662020<br/>
70759555626401852588078440691829064124951508218929855914917618450280848912<br/>
00728449926873928072877767359714183472702618963750149718246911650776133798<br/>
59095700097330459748808428401797429100642458691817195118746121515172654632<br/>
28221686998754918242243363725908514186546204357679842338718477444792073993<br/>
42365848238242811981638150106748104516603773060562016196762561338441436038<br/>
33904414952634432190114657544454178424020924616515723350778707749817125772<br/>
46796292638635637328991215483143816789988504044536402352738195137863656439<br/>
1212010397122822120720357<br/>
<br/>
Компилировать программу придётся не один год в распределённой сети из не одной тысячи машин :)]]></description>
			<pubDate>Tue, 02 Sep 2008 07:13:44 GMT</pubDate>
			<author>stab</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:12:03 shalomman</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919434</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919434</link>
			<description><![CDATA[получается что вместо одной проверки внутри вызываемой подпрограммы, мы делаем проверку перед каждым ее вызовом? Что мы тогда выигрываем в читабельности кода, если мы вынесли проверку из оной подпрограммы и разместили во всех местах ее вызова?]]></description>
			<pubDate>Tue, 02 Sep 2008 07:12:03 GMT</pubDate>
			<author>shalomman</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:09:29 tehnoman</title>
			<guid isPermaLink="true">#comment_919429</guid>
			<link>#comment_919429</link>
			<description><![CDATA[побольше бы таких статей на хабре!]]></description>
			<pubDate>Tue, 02 Sep 2008 07:09:29 GMT</pubDate>
			<author>tehnoman</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:06:57 shalomman</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919424</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919424</link>
			<description><![CDATA[очень интересен процесс модифицации кода(от рефакторинга, до изменения функционала), тестирования и дебага. Не смотря на парадигму «обязался — сделай» всеравно возможны ошибки, которые довольно просто найти используя валидацию. <br/>
Быть более конкретным — как я узнаю в большой системе почему «пирожки ее приготовления получились не очень вкусными и несовсем готовыми»?]]></description>
			<pubDate>Tue, 02 Sep 2008 07:06:57 GMT</pubDate>
			<author>shalomman</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:05:07 Gordon</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919418</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919418</link>
			<description><![CDATA[Интересный материал. Надо будет попробовать. Жду продолжения]]></description>
			<pubDate>Tue, 02 Sep 2008 07:05:07 GMT</pubDate>
			<author>Gordon</author>
		</item>
	

	
		<item>
			<title>02.09.2008 07:00:05 justonce</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919403</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919403</link>
			<description><![CDATA[Spec# как раз и пытается решить задачу статической проверки соблюдения контрактов еще на этапе компиляции]]></description>
			<pubDate>Tue, 02 Sep 2008 07:00:05 GMT</pubDate>
			<author>justonce</author>
		</item>
	

	
		<item>
			<title>02.09.2008 06:52:32 stab</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919386</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919386</link>
			<description><![CDATA[По-логике, все условия и инварианты должны быть статически проверяемые, т.е. все глюки отлавливаются на этапе компиляции. Но это только в теории, на практике две проблемы:<br/>
<br/>
1. Контракты формулируют довольно сложные математические теоремы над данными, автоматическое доказательство\опровержение которых, часто очень трудоёмкий\ресурсоёмкий (читай длительный) процесс. Компилировать исходник по часу не каждому понравится.<br/>
<br/>
2. Полная статическая проверка невозможна, т.к. в любой нетривиальной программе существуют внешние по отношению к программе данные (сокеты, файлы, консольный ввод, т.д.), на которые так просто статические ограничения не наложить, что приводит всё к той же концепции обработки исключений, а это как раз то от чего контракты нас пытются избавить.<br/>
<br/>
Несколько лет уже размышлю над контрактами, и чем больше думаю, тем чаще вспоминаю виртовский Оберон :)]]></description>
			<pubDate>Tue, 02 Sep 2008 06:52:32 GMT</pubDate>
			<author>stab</author>
		</item>
	

	
		<item>
			<title>02.09.2008 06:35:10 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919352</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919352</link>
			<description><![CDATA[самый простой пример, который пришел в голову…<br/>
<br/>
<blockquote>//вызывающая программа<br/>
…<br/>
<br/>
//обеспечиваем предусловия для вызываемого метода<br/>
if(String.IsNullOrEmpty(objectName) || objectName.Contains(«@»))<br/>
{<br/>
   //выводим сообщение об ошибке, прекращаем выполнение программы или передаем управление куда-либо<br/>
} <br/>
<br/>
SomeObject some = GetSomeObject(objectName);<br/>
<br/>
//т.к. мы выполнили предусловия по нашему контракту, то можем смело дергать методы объекта<br/>
//не боясь «object reference» исключения<br/>
Console.WriteLine(some.Name);<br/>
Console.WriteLine(some.Description);<br/>
<br/>
...</blockquote><br/>
<br/>
<blockquote>//вызываемая программа<br/>
<br/>
//нет необходимости выполнять проверку на пустую строку или еще на что-нибудь<br/>
//полагаемся на контракт<br/>
public SomeObject GetSomeObject(string objectName)<br/>
{<br/>
   //по условиям контракта должны вернуть объект<br/>
   SomeObject result = new SomeObject();<br/>
<br/>
   try<br/>
   {<br/>
      //собираем объект <br/>
   }<br/>
   catch(SomeException ex)<br/>
   {<br/>
      //не удалось собрать объект<br/>
      //но условия контракта выполнить надо<br/>
      result.Name = «Unknown name»;<br/>
      result.Description = «Can't find object»;<br/>
   }<br/>
   <br/>
   return result;<br/>
}</blockquote>]]></description>
			<pubDate>Tue, 02 Sep 2008 06:35:10 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:54:03 justonce</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919278</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919278</link>
			<description><![CDATA[Забавная штука — <a href="http://research.microsoft.com/SpecSharp/">research.microsoft.com/SpecSharp/</a>, как раз по теме. Вот только бы развили ее до промышленного уровня.<br/>
К сожалению нормально заработала у меня только на VS2008 SP1]]></description>
			<pubDate>Tue, 02 Sep 2008 05:54:03 GMT</pubDate>
			<author>justonce</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:51:51 Noofiz</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919270</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919270</link>
			<description><![CDATA[спасибо]]></description>
			<pubDate>Tue, 02 Sep 2008 05:51:51 GMT</pubDate>
			<author>Noofiz</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:39:51 DYPA</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919244</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919244</link>
			<description><![CDATA[приведите пожалуйста программеропонятный пример в котором показанно куда выкидывается валидация (кусочек вызывающей программы до и после).<br/>
]]></description>
			<pubDate>Tue, 02 Sep 2008 05:39:51 GMT</pubDate>
			<author>DYPA</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:31:58 dals</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919233</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919233</link>
			<description><![CDATA[Спасибо за интересный материал. Надеюсь, развитие темы не задержится? :)]]></description>
			<pubDate>Tue, 02 Sep 2008 05:31:58 GMT</pubDate>
			<author>dals</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:10:04 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919208</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919208</link>
			<description><![CDATA[Лекций, к сожалению, нет :(<br/>
Могу посоветовать вам почитать его книгу «Object-Oriented Software Construction», Bertrand Meyer, Prentice Hall, 2nd edition 1997.]]></description>
			<pubDate>Tue, 02 Sep 2008 05:10:04 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:08:19 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919206</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919206</link>
			<description><![CDATA[Да, валидацию я выкинул. Это как раз и есть основа принципа проектирования по контракту.<br/>
Очень много литературы учит нас использовать так называемое «защитное программирование» (defensive programming) (в следующих статьях постараюсь сделать сравнение обоих подходов).<br/>
Оно и говорит, что лучше на всякий случай перестраховаться и проверить (доверяй, но проверяй ;)).<br/>
А проектирование по контракту предлагает использовать некое соглашение, контракт, чтобы убрать лишние проверки (тем самым уменьшив объем кода и упростив читабельность программы).<br/>
Попробую привести пример из реальной жизни.<br/>
Допустим, наша компания производит слоеное тесто для выпечки пирогов. С конечным покупателем (читай, пользователем) мы заключаем такой контракт:<br/>
Если покупатель предварительно 15 минут разморозит наше тесто, затем сдобрит его маслом и будет выпекать в течении 10 минут, то у него получатся вкусные пирожки.<br/>
Т.е. мы обязуемся предоставить покупателю готовый продукт при выполнении некоторых условий.<br/>
<br/>
Но тут другая компания (ООО «СкоростьНашеВсе») решила помочь покупателям и продавать уже готовые горячие пирожки.<br/>
Она решила не тратить время на разморозку и выпекала всего 7 минут. В итоге, пирожки ее приготовления получились не очень вкусными и несовсем готовыми.<br/>
А вот тут уже конечному покупателю выбирать: покупать пирожки этой фирмы, обратится к другой или сделать все самому по инструкции (читай, контракту).<br/>
<br/>
Также и в случае программирования. Мы всю ответственность по передачи входных данных для нашей функции возлагаем на вызывающую программу.<br/>
При этом мы обязуемся ей вернуть валидные данные (если обещали вернуть double, то вернем double, а не null).<br/>
<br/>
Надеюсь, что теперь стал более понятен этот принцип.]]></description>
			<pubDate>Tue, 02 Sep 2008 05:08:19 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
		<item>
			<title>02.09.2008 05:08:04 ifa</title>
			<guid isPermaLink="true">http://habrahabr.ru/blogs/crazydev/38612/#comment_919204</guid>
			<link>http://habrahabr.ru/blogs/crazydev/38612/#comment_919204</link>
			<description><![CDATA[Конечно, возможны разные варианты. Например, можно обойтись вообще без генерации исключений. Например, предположим, что вызывающая программа ничего не знает (да и не должна знать) о классе ComponentInfo. Она его просто делегирует другому классу, который и производит различные манипуляции с этим объектом. Конечно, в этом случае генерация исключения в приведенном примере нам не подходит. Вот небольшой модифицированный примерчик этого:<br/>
<br/>
<blockquote>public ComponentInfo GetComponentInfo(string id)<br/>
{<br/>
   ComponentInfo info = new ComponentInfo();<br/>
   try<br/>
   {<br/>
     //собираем этот объект разными способами<br/>
    //с возможной генерацией исключения   <br/>
   }<br/>
   catch(ContractException ex)<br/>
   {<br/>
      //обеспечиваем возвращение валидного объекта<br/>
      info.Name = «Не известно»;<br/>
      info.Description = «Искомая деталь не найдена»;<br/>
      info.Price = 0;<br/>
   }<br/>
   return info;<br/>
}* This source code was highlighted with <a href="http://source.virtser.net">Source Code Highlighter</a>.</blockquote><br/>
<br/>
]]></description>
			<pubDate>Tue, 02 Sep 2008 05:08:04 GMT</pubDate>
			<author>ifa</author>
		</item>
	

	
</channel>
</rss>

