Цитата Сообщение от maratin Посмотреть сообщение
подскажите как реализовать следующий алгоритм на Owenlogic (для ПР200):
(индексация входных переменных)
на вход макроса подается несколько переменных типа "целое" (udint) - моточасы насоса -
A, B, C, D, E, F и соответствующие им выходные переменные Pa, Pb, Pc, Pd, Pe, Pf - очередность запуска насоса
значение каждой входной переменной: 0 (не готов к работе) или любое положительное число (наработка)
задача - присвоить каждой выходной переменной значения: ноль или возрастающее число от 1 до количества ненулевых входов:
0, если входная переменная равна 0
1, если входная переменная минимальная из всех положительных входных значений
2, если входная переменная минимальная из оставшихся переменных (без учета минимальной переменной, которой уже присвоили номер 1)
и т.д.
т.е. если на входе все >0, то на выходе должны быть значения от 1 до 6, без повторов (нулевых входов и выходов может быть несколько)
если на входе есть одинаковые значения, то меньший индекс получит вход, который ближе к началу алфавита
пример: вход -> выход
356 -> 4
16 -> 1
0 -> 0
88 -> 3
0 -> 0
16 -> 2
Код:
FUNCTION out: UDINT;
    VAR_INPUT
        In_Time1, In_Time2, In_Time3, In_Time4, In_Time5, In_Time6 : UDINT;
        enabl: BOOL;
    END_VAR
    
    VAR
        Queue, Data1, Data2 : ARRAY[1..6] OF UDINT;
        swOrder, swNumber, i, j, mini    : UDINT;
        f, sort    : BOOL;
    END_VAR
    
    IF enabl THEN
        Data1[1] := 1;
        Data1[2] := 2;
        Data1[3] := 3;
        Data1[4] := 4;
        Data1[5] := 5;
        Data1[6] := 6;
    
        Data2[1] := In_Time1;
        Data2[2] := In_Time2;
        Data2[3] := In_Time3;
        Data2[4] := In_Time4;
        Data2[5] := In_Time5;
        Data2[6] := In_Time6;
    
        FOR j:=1 TO 6 DO
            IF Data2[j] = 0 THEN Data2[j] := 4294967295; END_IF;
        END_FOR;
    
    
        FOR j:=1 TO 6 DO
            f := FALSE; mini := j;
            FOR i:=j TO 6-j DO
                IF Data2[i] > Data2[i+1] THEN
                    swOrder:= Data2[i];         swNumber:= Data1[i];
                    Data2[i] := Data2[i+1];    Data1[i] := Data1[i+1];
                    Data2[i+1] := swOrder;     Data1[i+1] := swNumber;
                    f := TRUE;
                END_IF;
                IF Data2[i] < Data2[mini] THEN mini := i; END_IF;
            END_FOR;
            IF NOT f THEN EXIT; END_IF;
            IF mini <> j THEN
                swOrder:= Data2[j];         swNumber:= Data1[j];
                Data2[j] := Data2[mini];     Data1[j] := Data1[mini];
                Data2[mini] := swOrder;     Data1[mini] := swNumber;
            END_IF;
        END_FOR;
    
        FOR j:=1 TO 6 DO
            IF Data2[j] = 4294967295 THEN
                Queue[Data1[j]] := 0;
            ELSE
                Queue[Data1[j]] := j;
            END_IF;
        END_FOR;
    
        out := Queue[1] * 100000 + Queue[2] * 10000 + Queue[3] * 1000 + Queue[4] * 100 + Queue[5] * 10 + Queue[6];
    
    END_IF;
    
END_FUNCTION
Порядок - в соответствующих десятичных разрядах