Помощь - Поиск - Пользователи - Календарь
Полная версия: Задача по электротехнике
Форум «Всё о Паскале» > Pascal, Object Pascal > Задачи
Иваныч
Задача такова:
Надо соединить 3 кнопки, 3 лампочки и 1звонок так, чтобы
при нажатии кнопки1 ( Кн1 ) загарается лампочка1 ( Л1 ) и звенит звонок,
при нажатии Кн2 загарается Л2 и звенит звонок,
и при нажатии Кн3 загарается Л3 и звени звонок.

Главная загвостка в том, что Лампочки(в последовательности) и звонок должны работать в полную силу.
Напряжение 220В
Кнопки с самовозвратом, 4 контактные (2 контакта на вкл состояние, и 2 на выкл)
Нельзя добавлять ничего лишнего(т.е конденсаторы, рэле, сопротивление и таму подобное)

Это всё будет ставится якобы в камуналке
Lapp
Ко всем, кто находит удовольствие в решении чисто программистских задач, просьба - дочитать этот мессадж до конца smile.gif.

Цитата(Иваныч @ 30.11.2008 19:12) *
Это всё будет ставится якобы в камуналке

Н-да.. smile.gif
Первой моей реакцией на эту тему было, ессно, перенести ее в Физику. Но потом я подумал, что возможно, что нужно не просто представить решение, а сделать способ нахождения такой схемы - то есть, программу smile.gif. И еще я подумал, что прога-то будет несложная. Ну, я и написал ее. А потом, счастливо улыбаясь, запустил... smile.gif

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

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

Вместе с неизменными атрибутами: Нажмите для просмотра прикрепленного файла

Ниже привожу саму программу. Написана на Obect Pascal, хотя это не очень существенно (никаких виртуальных методов). Приглашаю всех желающих приложить руку к ее оптимизации. Комментарии включены самые ограниченные, но я опишу подробно, если кто-то проявит интерес (и если сами не разберетесь smile.gif). Если кто-то предложит другой метод - более эффективный - ваще будет здорово smile.gif. Но в любом случае постарайтесь не ограничиваться словами..
Критика также принимается в любом (приличном) виде.
Желаю успеха!

uses
CRT;

var
n: integer; // Суммарное число контактов всех элементов
t: integer; // Номер следующего соединения при сборке

type
tVolt= (None,v1,v2); // Напряжение: не подано, v1, v2
tPin= array[1..255] of byte; // Массив выводов

tElement= object
mp: integer; // Число выводов
Pin: ^tPin; // Выводы
procedure Clear; // Отсоединение от всех шин
procedure Connect(p,b: byte); // Параметры: вывод, шина
function Connected: string; // Возвращает строку номеров шин по пинам
constructor Create(ip: integer);
end;

// Устройство с двумя выводами (лампа, звонок)
tDevice= object(tElement)
function Active: boolean; // Возвращает true, если на приборе есть полное напряжение
constructor Create;
end;

// Переключатель с двумя парами контактов
tSwitch= object(tElement)
Pos: byte; // Состояние переключателя: 0, 1
procedure Connect(p,b:byte);
constructor Create;
end;

// Источник (батарея или розетка)
tPower= object(tElement) // Напряжение на выводах
Volt: array[1..2]of tVolt;
procedure Connect(p,b: byte);
constructor Create;
end;

var
Bus: array[1..255]of tVolt; // Массив шин (соединительных проводов)
Shorting: boolean; // Индицирует состояние короткого замыкания в схеме

procedure tElement.Clear;
var
i: byte;
begin
for i:=1 to mp do Pin^[i]:=0
end;

procedure tElement.Connect(p,b: byte);
begin
if p<=mp then Pin^[p]:=b;
Inc(t);
end;

function tElement.Connected: string;
var
i: integer;
s,t: string;
begin
s:='';
for i:=1 to mp do begin
Str(Pin^[i]:5,t);
s:=s+t;
end;
Connected:=s
end;

constructor tElement.Create(ip: integer);
var
i: integer;
begin
mp:=ip;
Inc(n,mp);
GetMem(Pin,mp);
for i:=1 to mp do Pin^[i]:=0;
end;

constructor tDevice.Create;
begin
tElement.Create(2);
end;

function tDevice.Active: boolean;
begin
Active:=(Pin^[1]>0)and(Pin^[2]>0)and(Bus[Pin^[1]]<>None)and(Bus[Pin^[2]]<>None)and(Bus[Pin^[1]]<>Bus[Pin^[2]])
end;

constructor tSwitch.Create;
begin
tElement.Create(4);
end;

procedure tSwitch.Connect(p,b:byte);
var
i:byte;
begin
tElement.Connect(p,b);
case p of
1,2: i:=Pin^[3-p];
3,4: i:=Pin^[7-p]
end;
if Pos=(p-1)div 2 then begin
if i>0 then
if Bus[b]=None then Bus[b]:=Bus[i]
else if Bus[i]=None then Bus[i]:=Bus[b]
else Shorting:=Shorting or(Bus[b]<>Bus[i]);
end
end;

constructor tPower.Create;
begin
tElement.Create(2);
Volt[1]:=v1;
Volt[2]:=v2
end;

procedure tPower.Connect(p,b: byte);
begin
tElement.Connect(p,b);
if Bus[b]=None then Bus[b]:=Volt[p] else Shorting:=Bus[b]<>Volt[p]
end;

const
nn=100; // Максимально возможное суммарное число контактов всех элементов
m= 2; // Число ламп (равно числу переключателей)

var
Lamp: array[1..m]of tDevice;
Switch: array[1..m]of tSwitch;
Bell: tDevice;
Power: tPower;
Sw: tSwitch;
c: array[1..nn]of integer;
Correct: boolean;
k: integer;


procedure Show;
var
i: integer;
begin
for i:=1 to n do Write(c[i]:3);
WriteLn
end;

// Перебор всех возможных комбинаций подключений
procedure Next;
var
i,j: integer;
b: boolean;
begin
repeat
b:=false;
repeat
i:=0;
repeat
Inc(i);
if c[i]=k then c[i]:=1 else Inc(c[i])
until (c[i]<>1)or(i=n);
if Odd(i) and(c[i]=c[i+1]) then for j:=1 to i-1 do c[j]:=k else b:=true
until b;
for j:=1 to (i-1)div 2*2 do if Odd(j) then c[j]:=2;
j:=0;
for i:=1 to n do if c[i]=k then begin
Inc(j);
if j=2 then break
end
until j>1
end;

var
s: string;
i,j,p,a,t0: byte;
h: char;
Debug: boolean;

begin
Debug:=true;
Power.Create;
for i:=1 to m do begin
Lamp[i].Create;
Switch[i].Create;
end;
Bell.Create;
Power.Connect(1,2);
Power.Connect(2,1);
k:=2;
repeat
Inc(k);
WriteLn('Buses: ',k);
// Начальная конфигурация соединений
c[1]:=k;
c[2]:=1;
c[3]:=k;
for i:=3 to n do c[i]:=i mod 2+1;
// Основной цикл перебора
repeat
if Debug or KeyPressed then begin
h:=ReadKey;
if h=#13 then Debug:=not Debug;
Show
end;
// Разборка схемы
for i:=1 to m do Lamp[i].Clear;
Bell.Clear;
// Сборка схемы (лампы и звонок)
t:=1;
for i:=1 to m do begin
Lamp[i].Connect(1,c[t]);
Lamp[i].Connect(2,c[t]);
end;
Bell.Connect(1,c[t]);
Bell.Connect(2,c[t]);
t0:=t;
Shorting:=false;
Correct:=true;
// Цикл по состояниям кнопок (0 - ничего не нажато)
for a:=0 to m do if not Shorting then begin
for i:=3 to k do Bus[i]:=None;
for i:=1 to m do if i=a then Switch[i].Pos:=1 else Switch[i].Pos:=0;
for i:=1 to m do Switch[i].Clear;
for j:=1 to m do begin
t:=t0;
for i:=1 to m do {if not Shorting then} begin
Switch[i].Connect(1,c[t]);
Switch[i].Connect(2,c[t]);
Switch[i].Connect(3,c[t]);
Switch[i].Connect(4,c[t]);
end
end;
Correct:=Correct and not Shorting;
// Проверка работы схемы
for i:=1 to m do Correct:=Correct and (Lamp[i].Active=(a=i));
Correct:=Correct and (Bell.Active=(a>0))
end;
if not Correct then Next;
until Correct or (c[n-1]=3) or (h=#27)
until Correct or (h=#27);
if Correct then begin
Show;
WriteLn('Power: ',Power.Connected);
for j:=1 to m do begin
WriteLn('Lamp',j,': ',Lamp[j].Connected);
WriteLn('Switch',j,': ',Switch[j].Connected);
end;
WriteLn('Bell: ',Bell.Connected)
end
else WriteLn('Interrupted')
end.

P.S.
Время, может, не самое подходящее - типа сессия близко, но - who cares? smile.gif

P.P.S.
А не такая и мелкая, как мне казалось - рука устала елозить мышой, пока метил ее..
xds
Мое решение (интуитивное). Подходит для любого количества жильцов.

Нажмите для просмотра прикрепленного файла
andriano
Хочу отметить, что в условии не оговорено ни одного из следующих условий:
1. Возможности функционирования схемы при нажатии нескольких кнопок одновременно.
2. Сотношения между напряжением в сети и номинальными напряжениями лампочек и звонка.
Предлагаю схему:
Три цепочки из лампочки и последовательно соединенного с ней звонка включены в параллель.
Вся эта конструкция последовательно соединена со звонком.
При этом, естественно, номинальные токи лампочки и звонка должны быть равны, а напряжение в сети - сумме их номинальных напряжений.
Режим одновременного нажатия на кнопки схема не предусматривает так же, как и оба варианта, опубликованные ранее.
Достоинства схемы:
1. Легкость обобщения на произвольное количество лампочек и кнопок.
2. В конструкции допустимо использование "стандартных" кнопок, т.е. имеющих лишь одну пару контактов на замыкание (без размыкающих контактов).
Схема не лишена недостатков, в частности, перегрузка звонка в нештатном режиме работы (при замыкании нескольких кнопок одновременно). Но мне это кажется меньшим недостатком, чем то, что опережение замыкания перед размыканием (в штатном режиме) ведет к КЗ.
Lapp
Узнаю "раннего" andriano, готового спорить до бесконечности из-за никому неинтересных деталей.. smile.gif

Цитата(andriano @ 12.12.2008 23:35) *
Хочу отметить, что в условии не оговорено ни одного из следующих условий:
1. Возможности функционирования схемы при нажатии нескольких кнопок одновременно.
2. Сотношения между напряжением в сети и номинальными напряжениями лампочек и звонка.
... а также стандарты на изоляцию проводов, типы ламп и девичья фамилия бабушек жильцов.. smile.gif
Хорошо, я оговорю.
1. Одновременное нажатие кнопок запрещено и грозит выплатой полной стоимости оборудования (даже в случае его сохранности), плюс штраф в размере 2.71828 минимальных зарплат.
2. Номинальное значение напряжения ламп и звонка в точности равно напряжению в сети.
И добавлю от себя (по просьбе электрика Васи) еще один пункт:
3.14. ПАЛЬЦЫ В РИЗЕТКИ НЕСУВАТЬ!!!!!
smile.gif

Цитата(andriano @ 12.12.2008 23:35) *
Предлагаю схему:
Три цепочки из лампочки и последовательно соединенного с ней звонка включены в параллель.
Вся эта конструкция последовательно соединена со звонком.
При этом, естественно, номинальные токи лампочки и звонка должны быть равны, а напряжение в сети - сумме их номинальных напряжений.
Режим одновременного нажатия на кнопки схема не предусматривает так же, как и оба варианта, опубликованные ранее.
Ты лучше нарисуй, хотя мне уже не нравятся слово "последовательно" и подозреваемая мной множественность звонков..

Цитата(andriano @ 12.12.2008 23:35) *
Достоинства схемы:
1. Легкость обобщения на произвольное количество лампочек и кнопок.
Схема xds делает это с блеском.

Цитата(andriano @ 12.12.2008 23:35) *
2. В конструкции допустимо использование "стандартных" кнопок, т.е. имеющих лишь одну пару контактов на замыкание (без размыкающих контактов).
... ибо контакты на размыкание безумно дороги в производстве, что особенно существенно при гигантских масштабах нашего Проекта.. smile.gif

Цитата(andriano @ 12.12.2008 23:35) *
Схема не лишена недостатков, в частности, перегрузка звонка в нештатном режиме работы (при замыкании нескольких кнопок одновременно). Но мне это кажется меньшим недостатком, чем то, что опережение замыкания перед размыканием (в штатном режиме) ведет к КЗ.
Если таковые (двойные) кнопки выпускаются производством, они должны быть сертифицированы и гарантированы от подобных нештатных ситуаций.

Ладно, хватит шутить - andriano, ты правда не видишь, что задача имеет чисто академический характер? Решение привел xds, решение правильное и т.д. и т.п.. Но!

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

Моя программа - не Бог весть какое чудо, но она все же вносит некоторое разнообразие в бесконечные "расставить сторки по.." Она решает только эту конкретную задачу, причем за непозволительно большое время, но все же дает некоторое понятие о неких других задачах, которые могут решаться программным способом. Я надеялся на дискуссию именно по программированию, а не по физике (когда я начал решать ее программно, я как бы заблокировал себе мысли об обычном решении). Что ж, не вышло.. Наверное, надо действительно перенести тему в Физику, а свой пост опубликовать отдельно в FAQ - хотя, я не назвал бы этот вопрос часто задаваемым.. я подумаю. Чего и вам желаю..

Take it easy! smile.gif
andriano
Цитата(Lapp @ 13.12.2008 0:35) *

Узнаю "раннего" andriano, готового спорить до бесконечности из-за никому неинтересных деталей.. smile.gif
...
Но мне очень жаль, что никто из ответивших не понял меня.. sad.gif
...
Задача провисела тут несколько дней, и ни у кого не появилось мысли ее решить.
...
Я надеялся на дискуссию
...

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

Я честно попытался прочитать программу, но, увы, не преуспел в этом.
Виной этому:
1. Во-первых - моя лень.
2. Во-вторых - то, что стиль написания несколько отличается от того, к которому я привык:
var
n: integer; // Суммарное число контактов всех элементов

Я бы не стал называть глобальную переменную однобуквенным идентификатором, но это в данном случае неважно, по крайней мере. на данном этапе еще не помешало погиманию, а вот это:
  t: integer; // Номер следующего соединения при сборке

я действительно не могу понять. Из 4-х слов понимаю смысл только первого. Что такое соединение? Каким образом они нумеруются? (хотя бы в пределах одной схемы или в процессе перебора по разным вариантам схем) Что такое сборка?
type
tVolt= (None,v1,v2); // Напряжение: не подано, v1, v2

Правильно ли я перевел на "свой" язык?
type
tVolt= (None, LoV, HiV); // Напряжение на контакте: не подключен, низкий уровень, высокий уровень


  tPin= array[1..255] of byte;          // Массив выводов
Как соотносятся между собой выводы и контакты?
Что означает каждое из 255 вариантов значения вывода?
    constructor Create(ip: integer);

Что обозначает входная переменная?
    Pos: byte;                          // Состояние переключателя: 0, 1

Почему переменная, принимающая только два значения, имеет тип byte, а не boolean?
И какой цифре соответствует состояние "замкнуто", а какой "разомкнуто"? (интуитивно кажется 1 и 0 соответственно, но хотелось бы знать наверняка)

И, на мой взгляд, в программе катастрофически не хватает комментариев: мне представляется, что КАЖДЫЙ заголовок процедуры или функции должен сопровождать описанием ее назначения, а также описанием каждого из параметров.
Общая доля комментариев в коде, если не ошибаюсь, должно составлять около 30%.

Прошу понять меня правильно: я не высказываю претензий к автору, я пытаюсь объяснить, почему я не стал разбираться в этой программе. (т.к. автор высказывает претензии ко мне - почему не прочитал и не разобрался?)
-Владимир-
Схема не будет работать. При включении любой из кнопок, гореть будут все лампочки так как питание будет проходить через лампочки.
-Ваня-
Цитата(xds @ 12.12.2008 17:55) *

Мое решение (интуитивное). Подходит для любого количества жильцов.

Нажмите для просмотра прикрепленного файла


схема работает, автору респект)
Гость
Цитата(-Ваня- @ 7.09.2019 2:42) *

Цитата(xds @ 12.12.2008 17:55) *

Мое решение (интуитивное). Подходит для любого количества жильцов.

Нажмите для просмотра прикрепленного файла


схема работает, автору респект)


Валерий.
Очень интересно! Это схему задачу я решал в 1973 году на Дальнем Востоке.
Просидел над ней целый месяц.
В конце концов решил её и на этом принципе мы построили много схем по управлению компрессорами.
Тогда не было ни компьютеров, не Pascal.
Это текстовая версия — только основной контент. Для просмотра полной версии этой страницы, пожалуйста, нажмите сюда.