Vai al contenuto
PLC Forum


Unity - Confrontare Un Array Diverso Da Zero


marco.f

Messaggi consigliati

per realizzare un bit di presenza allarme voglio vedere se uno qualsiasi degli elementi del mio array di allarmi è diverso da zero ma le istruzioni che ho trovato mi dicono solo se incontro un valore superiore (FIND_GT_***) o Inferiore (FIND_LT_***) a quello dato.

devo utilizzare tutte e due le istruzioni o esiste una soluzione migliore?

preferirei utilizzare solo il linguaggio ladder.

Grazie per l'aiuto.

Link al commento
Condividi su altri siti


la prima cosa che mi viene in mente è:

fai la somma di tutti gli elementi dell'array. Se è diversa da zero allarme.

oppure esegui l'AND di word tra tutti gli elementi dell'array e 16#FFFF . Se il risultato diverso a 0 allarme

Link al commento
Condividi su altri siti

fai:

SUM_ARINT (tuo array in ingresso; il risultato su un INT) sull'ENO metti COMPARE "risultato<>0" allora bit di allarme

oppure:

EQUAL_ARINT (tuo array IN1; array identico sempre a 0 IN2; P = 0; array risultante su OUT) sull'ENO metti COMPARE "risultato<>-1" allora bit di allarme

Link al commento
Condividi su altri siti

oppure esegui l'AND

L'AND è indicato se si cercano gli "1", per testare se tutto è a 0 bisigna fare OR.

Memento: AND forza gli zeri, OR forza fli 1.

Es.: 000.0010 AND 0000.0000 = 0000.0000

000.0010 OR 0000.0000 = 0000.0010

Modificato: da Livio Orsini
Link al commento
Condividi su altri siti

certo Livio, però nota che io ho suggerito l'AND con tutti i bit a 1 (16#ffff), quindi il risultato è identico all'OR di bit a 0.

Ad ogni modo per eseguire il minor numero di istruzioni (come mi sembra che chieda) sono migliori i metodi prima suggeriti, perchè mi sembra (cercherò bene) che con Unity le istruzioni AND o OR su array (con le istruzioni della libreria) mettano il risultato ancora su array, dunque il problema di testare se almeno un bit a 1 è presente si ripropone.

Link al commento
Condividi su altri siti

Innanzitutto grazie per le pronte risposte.

Non c'è un'istruzione di OR tra bytes?

Purtroppo non ho trovato un istruzione simile, ma solo istruzioni che eseguono operazioni logiche tra 2 diversi arrray o tra un array e una variabile, ma il risultato è comunque un ulteriore array, quindi mi troverei nella situazione di partenza.

SUM_ARINT (tuo array in ingresso; il risultato su un INT) sull'ENO metti COMPARE "risultato<>0" allora bit di allarme

c'è una cosa che non capisco: anche se faccio la somma di tutti gli elementi che lo compongono, cosa mi garantisce di avere tutto l'array a 0 pur ottenendo un risultato uguale a zero?

se gli interi possono andare da -32768 a +32767 la sfortuna (che come tutti sanno ci vede benissimo...) potrebbe farmi ritrovare con due numeri uguali di segno opposto, e a quel punto non genererei il bit di allarme presente.

la soluzione dell'EQUAL_ARINT mi sembra più sicura, ma comunque abbastanza macchinosa.

Almeno quanto la prima che mi era venuta in mente, ovvero confrontare l'array ed una variabile a zero prima con FIND_GT_ARINT poi con FIND_LT_ARINT quindi se in uno dei due casi la risultante è <> da -1 generare il bit di allarme.

cosa dite può funzionare anche questa?

Comunque sembra strano che un programma potente come unity si incarti su operazioni del genere che a mio giudizio sono abbastanza comuni.

Ciao e grazie di tutto.

Link al commento
Condividi su altri siti

unity si incarti su operazioni del genere che a mio giudizio sono abbastanza comuni.

Dov'è che si incarta scusa! devi eseguire 2 istruzioni eh.

ma comunque abbastanza macchinosa

macchinoso? sono due operazioni!!! non devi far nulla di più!

Perdonami ma i tuoi confronti LT e GT sono macchinosi non credi?

Ad ogno modo se non ti piace la soluzione EQUAL_ARINT e vuoi un unico univoco solo blocco funzione, hai la possibilità di scrivertelo e salvartelo in libreria.

Metodi per fare quello che vuoi possono essere matematici o logici attraverso dei loop ecc. vedi tu di sopperire a ciò che Unity non ti permette di fare.

Link al commento
Condividi su altri siti

prova a vedere se ti piace di più così.

Senza lavorare con istruzioni sugli array ma usandone semplicemente i suoi elementi. Istruzione EQ (te lo rappresento in ST)

I dati sono:

array di 5 DINT di allarmi = allarmi

Bit che a 1 significa tutto ok = nessun_allarme

IF allarmi[0]=0 THEN

nessun_allarme := EQ (

IN1 := allarmi[1],

IN2 := allarmi[2],

IN3 := allarmi[3],

IN4 := allarmi[4]

);

END_IF;

Ma ci sono 1000 modi........

Link al commento
Condividi su altri siti

calma calma, non volevo urtare la sensibilita di nessuno, quando ho detto "incartare" non intendevo che il software non fosse in grado di compiere le operazioni, mi meravigliavo solamente che pur possedendo istruzioni potentissime, non ce ne fosse una per il confronto di un array <> da un valore dato.

dipenderà da come lavora unity, ma lo trovo comunque strano, come ad esempio il fatto che per copiare degli i-o su aree di memoria si debba usare MOVE_AR_BOOL, mentre con twido suite, infinitamente meno performante basti una semplice assegnazione %mw := %iw.

comunque se avessi avuto solo 5 dw di allarmi mi sarei fatto i miei 5 buoni operate e fine, il problema è che ho qualcosa come 100 word da controllare e allora risulta un po scomodo.

Grazie comunque dell'aiuto (ho poi usato la soluzione EQUAL_ARINT dato che non ho problemi di memoria)

Ciao.

Link al commento
Condividi su altri siti

basti una semplice assegnazione %mw := %iw

beh ma non esiste l'indirizzo %IW per ingressi digitali.

Comunque siccome capisco a cosa ti riferisci in generale, devi pensare che ci sono regole dettate dalla norma IEC 1131-3 e non meno importante dovresti "pensare" diversamente.

Molto semplicemente dovresti diciamo "convincerti" che scrivere

:=

oppure

MOVE_AREBOOL_INT

è la stessa cosa. Eseguono la stessa operazione ma scritta in due modi differenti

calma calma, non volevo urtare la sensibilita di nessuno

hai ragione mi sono un po' scaldato... non è che urti la mia sensibilità, sai che me ne importa di Unity o altro... secondo me quello che hai avuto è l'approccio sbagliato .. Un software ti dà tutti gli strumenti (funzioni elementari) per fare qualsiasi cosa, tanta grazia che ora esistono tante funzioni complesse già sviluppate. La tua è una funzione complessa tra le tante ed oltre a non essere così banale non è nemmeno poi così comune tanto da essere standardizzata. Perlomeno non più di altre (quelle che fanno parte delle librerie).

In conclusione dire che un software "s'incarta" per il fatto di non avere già sviluppata una funzione qualsiasi di quelle non basilari non è corretto.

Va beh.. l'importante è che hai risolto e tutto funziona.

Ciao

Link al commento
Condividi su altri siti

marco.f wrote :

c'è una cosa che non capisco: anche se faccio la somma di tutti gli elementi che lo compongono, cosa mi garantisce di avere tutto l'array a 0 pur ottenendo un risultato uguale a zero?

se gli interi possono andare da -32768 a +32767 la sfortuna (che come tutti sanno ci vede benissimo...) potrebbe farmi ritrovare con due numeri uguali di segno opposto, e a quel punto non genererei il bit di allarme presente.

Questo problema si può risolvere dichiarando un array di UINT (al posto di INT).

Link al commento
Condividi su altri siti

biros66 wrote:

100 Word di allarmi --------------- x 16 Bit = 1600 Allarmi

hai costruito il controllo infallibile, oppure gestisci una centrale nucleare?

Se usati tutti certo non sono pochi, se usati con un criterio tabellare sicuramente hanno un loro perché ....

Ovvero 100 word per 100 utenze :

W0:X0 = Termica Utenza1, W0:X1=Mancato Avvio Utenza01,W0:X2=Max Ore Funzionamento Utenza01

W1:X0 = Termica Utenza2, W1:X1=Mancato Avvio Utenza02,W1:X2=Max Ore Funzionamento Utenza02

e così via.

Io adotto questo sistema e lo trovo molto lineare (e anche vero che non uso più di 3-4 bit di allarme per utenza).

Link al commento
Condividi su altri siti

hai costruito il controllo infallibile, oppure gestisci una centrale nucleare?

In realtà è una "semlpice" anche se estesa applicazione di building automation :rolleyes:

comunque diverse word, sono riservate e non ancora utilizzate, ma non vorrei andare a ricontrollare la gestione di presenza allarmi ogni volta che devo aggiungere un interruttore... ^_^

Link al commento
Condividi su altri siti

Crea un account o accedi per commentare

Devi essere un utente per poter lasciare un commento

Crea un account

Registrati per un nuovo account nella nostra comunità. è facile!

Registra un nuovo account

Accedi

Hai già un account? Accedi qui.

Accedi ora
×
×
  • Crea nuovo/a...