?

Log in

No account? Create an account

Об обучении программированию [3]

« previous entry | next entry »
Jan. 16th, 2008 | 02:06 pm



Продолжение. См. начало.




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

Эта концепция стоит в основе процедурных языков (от машинного выполнения и вплоть до высот самых сложных языков вроде C++). Попытаюсь её проиллюстрировать несколькими _контр_примерами (в двух я не сумел помочь, хотя пытался, а в одном - сумел, хоть и не стремился):

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

X=X+1


Выяснение контекста приводит к слову "Фортран"... ага, ясно. Сначала долго объяснял, что это - присваивание (а не утверждение равенства и не сравнение), а потом - чему равен X "до", и чему "после"... и вот тут наступил ступор. Сейчас бы я, скорее всего, пошёл по формально-математическому пути: есть "состояние исполнителя", в котором можно определить "переменные", и вот это состояние определённым образом изменяется при каждом выполнении "функции" одного шага исполнителя. Но дал бы что-то этот путь в случае математического мышления ученика? Всё равно нужно сделать так, чтобы что-то облегчало мышление в процедурном стиле.

(Я тут откровенно растекаюсь мысью по древу, но сейчас отвлёкся в вот какую сторону: чем хорош интерактивный отладчик и почему его многие любят несмотря на то, что как инструмент поиска ошибки он далеко не всегда лучший? Кажется, знаю ответ: именно потому, что подсветка (стрелкой, цветом, etc.) даёт _визуальную_ поддержку понятия текущего места исполнения. Что способствует структуризации мышления в нужную сторону.)

Текущее место исполнения, плюс условный "метроном" исполнения, тикающий на каждый шаг - вероятно, достаточно для многих, чтобы представить себе ход работы программы. Далее - одним интуитивно, другим с явно высказанной концепцией "состояния" - должно было прийти достаточное понимание, чтобы понимать хотя бы простейшие тесты вида


a := 10;
b := 20;
a := b;
print(a); // что выведет print?


С одноклассником я, похоже, не достиг хорошего результата - школьную информатику (ещё ершовского образца) он прошёл кое-как и, видимо, решил в эту сторону больше не идти. Когда я последний раз про него что-то слышал, он держал книготорговую фирму. А я сейчас думаю: а если бы был выбор между процедурными языками и функциональными - может, на функциональном он бы лучше понял тематику? Математиком-то он был отличным... только вот ближайшее что я мог предложить - это Lisp, и то на бумаге.

Второй пример, тоже из провальных - уже вуз. Однокурсник жены, радиофизик... не знаю, насколько это влияет. Составляет программу - итеративное вычисление функции, на входе и выходе у которой две переменные (можно назвать это двумя функциями - непринципиально), есть критерий остановки. На уровне общего подхода, полный аналог задачи - вычисление наибольшего общего делителя. Он берёт массивы и... начинает их заполнять, примерно так:

a[0] := A; b[0] := B;
i = 1;
while (продолжаем) {
  a[i] := f1(a[i-1], b[i-1]);
  b[i] := f2(a[i-1], b[i-1]);
}


Из объяснений я понял, что он уже представляет себе, что значения в массивах не определены до тех пор, пока не было присвоения. Но то, что одному элементу или переменной можно последовательно присвоить разные значения, и предыдущее пропадёт - оказалось выше его понимания. И это был, как я осознаю сейчас, ещё один пример, как можно было чего-то добиться обучением начиная с функционального стиля, а не с процедурного. Назначение (binding) он понял сразу. Присвоение - нет.

Третий пример - не из программирования, но по сути о том же. Один знакомый на пару курсов младше (страшный разгильдяй) попросил у меня конспект - выучить и сдать предмет. Я предупредил: у меня нестандартная и совершенно специфическая система сокращений и обозначений, он ничего не поймёт. "Ничего", - сказал он, - "попробую". Через неделю возвращает довольный - говорит, по моему конспекту всё понял и смог сдать на твёрдую тройку (что для него было достижением;)) лучше чем по всем остальным, какие смог найти. Я почти в шоке, начинаем разбираться. Нашли следующие факторы:

1. То, что я тогда добросовестно всё посещал и записывал.
2. То, что обычно хватало времени на то, чтобы всё записать, наверно, благодаря той же системе сокращений.
3. Совет Трофимчука (кибфак поймёт;)) - "Если не хватает времени записывать всё - записывайте не формулы, а слова, которые произносятся между ними. Формулы вы найдете в любом учебнике."
4. Наконец, такая вроде бы мелочь. Как _записать_ (причём без лишних слов) введение нового обозначения? Типичное для промежуточных этапов назначение в стиле "обозначим a^2+3*x*b^3 как z". Что делает... мнэээ... добросовестная девочка (это такой метатип;)), записывая за лектором? Слов в этот момент много, появляется поэтому только формула: "z = a^2+3*x*b^3". А как теперь определить, что это "=" значит - назначение, проверяемое уравнение, уже доказанное уравнение? Заново продумывать всю логику? Так и этого недостаточно - вспоминая курс Оптимальное управление", к которому требовался при полном изложении ещё примерно семестр особой математики, который благополучно похерили (так что я сомневаюсь, что хотя бы три человека с курса его поняли. я не понял.) А я использовал в таком случае знаки ":=" или, наоборот, "=:", что было однозначно понятно любому читающему - что мы тут _назначили_ соответствие. Разумеется, для доказанного и других вариантов были другие знаки.)

В то же время практически все наши преподаватели не могли понять, зачем (на доске) надо что-то особо обозначать - откуда это возникло. Чуть отвлёкся - и на доске тебе абстрактный знак равенства. Сиди и думай, к чему оно... Нет, я безусловно верю, что нормальный студент должен после лекции сам всё продумать, проверить, проработать все промежуточные этапы... но это уже другая тема. А на дворе было начало 90-х.

Так вот - про себя я знаю, что мне в процедурном стиле мыслить легче, чем в функционально-декларативном. Но о чём говорит восприятие моего... мнэээ... коллеги - просто о достаточном уровне разгильдяйства, или же то, что и ему мой стиль "прежде чем что-то использовать, надо определить, откуда и как оно возникло" близок именно из-за его чёткого "временнОго" характера? Или там на самом деле нет явной связи со временем?

Link | Leave a comment |

Comments {24}

_slw

(no subject)

from: _slw
date: Jan. 16th, 2008 12:28 pm (UTC)
Link

Так вот - про себя я знаю, что мне в процедурном стиле мыслить легче, чем в функционально-декларативном. Но о чём говорит восприятие моего... мнэээ... коллеги - просто о достаточном уровне разгильдяйства, или же то, что и ему мой стиль "прежде чем что-то использовать, надо определить, откуда и как оно возникло" близок именно из-за его чёткого "временнОго" характера? Или там на самом деле нет явной связи со временем?

вообще-то это и есть процедурный стиль, не?

по крйне мере мне он более понятен, как и процедурное программирование.

Reply | Thread

netch

(no subject)

from: netch
date: Jan. 16th, 2008 01:21 pm (UTC)
Link

> вообще-то это и есть процедурный стиль, не?

Вот я и хочу, чтобы кто-то более грамотный сказал мне, оно или нет:)

Reply | Parent | Thread

(no subject)

from: growler
date: Jan. 16th, 2008 02:12 pm (UTC)
Link

на самом деле, все люди изначально предрасположены к функциональному программированию
потому что в каждом живет Искра Божья
но потом тяжелый жизненный опыт настраивает мозг на императивный стиль
когда программист снова начинает думать в функциональном стиле, он испытывает настоящее откровение
потому что возвращается к истокам

Reply | Parent | Thread

_slw

(no subject)

from: _slw
date: Jan. 16th, 2008 02:22 pm (UTC)
Link

а меня от функциональщины на проблёв тянет

Reply | Parent | Thread

netch

(no subject)

from: netch
date: Jan. 16th, 2008 03:23 pm (UTC)
Link

Ты не уверовал в Него :)

Reply | Parent | Thread

Александр Соловьёв

(no subject)

from: p1r4nh4
date: Jan. 16th, 2008 03:30 pm (UTC)
Link

В каком смысле "функциональщины"? Ну, типа, пример можно, от которого можно проблеватся?

Reply | Parent | Thread

_slw

(no subject)

from: _slw
date: Jan. 16th, 2008 05:07 pm (UTC)
Link

а сразу как вижу -- так и блевать тянет.

Reply | Parent | Thread

Александр Соловьёв

(no subject)

from: p1r4nh4
date: Jan. 17th, 2008 08:12 am (UTC)
Link

:-)))

Reply | Parent | Thread

netch

(no subject)

from: netch
date: Jan. 16th, 2008 02:33 pm (UTC)
Link

Неужели Бог думал функциями?

Reply | Parent | Thread

Александр Соловьёв

(no subject)

from: p1r4nh4
date: Jan. 16th, 2008 03:27 pm (UTC)
Link

<бог>: дьявол, го в людей. я создал.

Reply | Parent | Thread

netch

(no subject)

from: netch
date: Jan. 16th, 2008 03:32 pm (UTC)
Link

Это процедурщина, по-моему

Reply | Parent | Thread

Александр Соловьёв

(no subject)

from: p1r4nh4
date: Jan. 16th, 2008 03:39 pm (UTC)
Link

Это стратегия... ;-) А в некоторых случаях тактика. А так же бывали случаи 3д-экшена.

Мешанина, одним словом. ;-)

Reply | Parent | Thread

(no subject)

from: growler
date: Jan. 16th, 2008 04:30 pm (UTC)
Link

это очевидно, по-моему

функция описывает, что должно получиться
а процедура описывает, как именно это должно получиться

не Божье это дело -- писать атомам инструкции
изначальное Слово было функцией
и её теперь вычисляет целая вселенная
(может, кстати, результатом будет и 42)

так и у функциональных программистов
главное, функцию описать
а уж её на последовательные инструкции разложить компилятор постарается

Reply | Parent | Thread

netch

(no subject)

from: netch
date: Jan. 16th, 2008 04:47 pm (UTC)
Link

Ну в этом смысле он даже не функциями думал...

Reply | Parent | Thread

Александр Соловьёв

(no subject)

from: p1r4nh4
date: Jan. 17th, 2008 08:21 am (UTC)
Link

Декларативное программирование, больше ничего не скажешь. :-)

Reply | Parent | Thread

oal

(no subject)

from: oal
date: Jan. 16th, 2008 03:22 pm (UTC)
Link

«:=» — тема. Всегда ставил именно его в соотвутствующих местах в конспекте и ни разу не пожалел.

Reply | Thread

(no subject)

from: palm_mute
date: Jan. 16th, 2008 03:30 pm (UTC)
Link

>Второй фактор - понимание концепции "состояния, зависящего от времени" (опять же, на достаточно абстрактном уровне).
Мне кажется, что функциональные программисты понимают природу изменяемого состояния глубже.

>прежде чем что-то использовать, надо определить, откуда и как оно возникло
А где здесь "временной характер"? Больше на зависимость по данным похоже.

Reply | Thread

(no subject)

from: gds
date: Jan. 16th, 2008 04:17 pm (UTC)
Link

по прочтении поста -- удивлен и доволен (даже не могу сформулировать, чем). Но хотя бы тем доволен, что концепция mutable values не является естественной для человека, знакомого с математикой.

я вспомнил ещё книжку типа "C для идиотов", так там весьма подробно освещались переменные: ящичек рисовался псевдографикой, в ящичек сначала клали, а потом из него доставали. Возможно эта метафора будет полезной, если придётся.

а Вы долго разбирались в работе декларативного make? Вообще, интересны первые впечатления про make.

Reply | Thread

netch

(no subject)

from: netch
date: Jan. 16th, 2008 04:46 pm (UTC)
Link

> концепция mutable values не является естественной для человека, знакомого с математикой.

Она совершенно естественна, но в других областях (ну например - сегодня в кармане сигареты, а завтра записная книжка). Проблема в выражении её в явном виде для того, кто встречал её только неявно.

> а Вы долго разбирались в работе декларативного make? Вообще, интересны первые впечатления про make.

Увы, эксперимент нечистый - я перед этим уже читал книжки по Прологу.

Reply | Parent | Thread

Денис

(no subject)

from: mithraen
date: Jan. 16th, 2008 10:09 pm (UTC)
Link

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

Его поведение (если не использовать различные сложные расширения) просто очевидно.

Однако опыт запуска make -j<что-нибудь большое> показывает что таки далеко не для всех очевидно.

Reply | Parent | Thread

No hugging no learning

(no subject)

from: ormuz
date: Jan. 17th, 2008 10:44 am (UTC)
Link

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

Сейчас-то чего, программирование стало вроде езды на велосипеде, неделю потыкался в интерпретаторе и все понятно. Всё дело в этой неделе.

Да и, честно говоря, не уверен что существует и проблема обучения программистов. То есть, наверное существует, ровно в той степени в которой существует проблема обучения рисованию.
Можно ли научить рисовать безталанного меня? Наверное можно, но зачем?

Reply | Thread

Maksym Shevchenko

(no subject)

from: r0land
date: Jan. 20th, 2008 10:32 pm (UTC)
Link

Ну... Я с 5-ого по 8-ой класс не мог понять что такое указатель и ссылка и в чем между ними разница....

Reply | Thread

kouzdra

(no subject)

from: kouzdra
date: Jan. 21st, 2008 03:14 pm (UTC)
Link

Забавно - я тоже когда-то столкнулся с аналогичной проблемой ("объяснить присваивание").

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

Мне проще в функциональном - не потому, что "естественнее", а потому что в программе при этом намного меньше неявных связей, за которыми надо следить. C точки зрения сложности они оказываются существенно проще.

Reply | Thread

(no subject)

from: i_not_bot
date: Dec. 25th, 2008 05:32 pm (UTC)
Link

Бесплатно скачать учебники по точным наукам: Литература для физ-мата

Reply | Thread