Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Скачиваний:
41
Добавлен:
11.10.2020
Размер:
3.04 Mб
Скачать

10 - ANHANG

Anhang C Datentypen in CoDeSys

Der Benutzer kann Standard Datentypen und selbstdefinierte Datentypen beim Programmieren verwenden. Jedem Bezeichner wird ein Datentyp zugeordnet, der festlegt, wie viel Speicherplatz reserviert wird und welche Werte dem Speicherinhalt entsprechen.

10.14 Standard Datentypen

BOOL

Variablen vom Datentyp BOOL können die Wahrheitswerte TRUE und FALSE annehmen. Es werden 8 Bit Speicherplatz reserviert.

Ganzzahlige Datentypen

Zu den ganzzahligen Datentypen gehören BYTE, WORD, DWORD, SINT, USINT, INT, UINT, DINT,

UDINT.

Die unterschiedlichen Zahlentypen decken einen unterschiedlichen Zahlenbereich ab. Für die ganzzahligen Datentypen gelten die folgenden Bereichs grenzen:

Typ

Untergrenze

Obergrenze

Speicherplatz

BYTE

0

255

8 Bit

WORD

0

65535

16 Bit

DWORD

0

4294967295

32 Bit

SINT:

-128

127

8 Bit

USINT:

0

255

8 Bit

INT:

-32768

32767

16 Bit

UINT:

0

65535

16 Bit

DINT:

-2147483648

2147483647

32 Bit

UDINT:

0

4294967295

32 Bit

Dadurch kann es passieren, dass bei der Typkonvertierung von größere auf kleinere Typen Information verloren geht.

REAL / LREAL

Die Datentypen REAL und LREAL sind so genannte Gleitpunkttypen. Sie sind nötig bei Verwendung von rationalen Zahlen. Der reservierte Speicherplatz beträgt 32 Bit bei REAL und 64 Bit bei LREAL.

STRING

Eine Variable vom Datentyp STRING kann eine beliebige Zeichenkette aufnehmen. Die Größenangabe zur Speicherplatzreservierung bei der Deklaration bezieht sich auf Zeichen und kann in runden oder eckigen Klammern erfolgen. Ist keine Größe angegeben, so werden standardmäßig 80 Zeichen angenommen.

Die String-Länge ist grundsätzlich nicht begrenzt, allerdings können die String-Funktionen nur Längen von 1-255 verarbeiten !

Beispiel einer Stringdeklaration mit 35 Zeichen: str:STRING(35):='Dies ist ein String';

CoDeSys V2.3

10-33

Standard Datentypen

Zeitdatentypen

Die Datentypen TIME, TIME_OF_DAY (kurz TOD), DATE und DATE_AND_TIME (kurz DT) werden intern wie DWORD behandelt.

Bei TIME und TOD wird die Zeit in Millisekunden angegeben, wobei bei TOD ab 00:00 Uhr gerechnet wird.

Bei DATE und DT wird die Zeit in Sekunden angegeben, wobei ab dem 1. Januar 1970 um 00:00 Uhr gerechnet wird.

Sehen Sie im folgenden die Zeitdatenformate für die Zuweisung (Zeitund Datumskonstanten):

ZeitkonstantenTIME

Eine TIME-Konstante besteht stets aus einem anführenden "t" oder "T" (bzw. "time" oder "TIME" in der ausführlichen Form) und einem Doppelkreuz "#".

Danach kommt die eigentliche Zeitdeklaration, diese kann bestehen aus Tagen (bezeichnet mit "d"), Stunden (bezeichnet mit "h"), Minuten (bezeichnet mit "m"), Sekunden (bezeichnet mit "s") und Millisekunden (bezeichnet mit "ms"). Es ist zu beachten, dass die Zeitangaben der Größe nach geordnet sein müssen (d vor h vor m vor s vor m vor ms), wobei nicht alle Zeiten vorkommen müssen.

Beispiele für korrekte TIME-Konstanten in einer ST-Zuweisung:

TIME1 := T#14ms;

 

TIME1 := T#100S12ms;

(*Überlauf in der höchsten Komponente ist erlaubt*)

TIME1 := t#12h34m15s;

 

nicht korrekt wäre:

 

TIME1 := t#5m68s;

(*Überlauf bei einer niedrigeren Stelle*)

TIME1 := 15ms;

(*Es fehlt T#*)

TIME1 := t#4ms13d;

(*falsche Reihenfolge der Zeitangaben*)

DATE-Konstanten, für Datumsangaben:

Eine DATE-Konstante wird deklariert durch ein anführendes "d", "D", "DATE" oder "date" und ein nachfolgendes "#". Anschließend können Sie ein beliebiges Datum in der Reihenfolge Jahr-Monat- Tag eingeben.

Beispiele:

DATE#1996-05-06 d#1972-03-29

TIME_OF_DAY-Konstanten, zum Speichern von Uhrzeiten:

Eine TIME_OF_DAY-Deklaration beginnt mit "tod#", "TOD#", "TIME_OF_DAY#" oder "time_of_day#", anschließend können Sie eine Uhrzeit angeben in der Schreibweise: Stunde:Minute:Sekunde. Sekunden können dabei als reelle Zahlen angegeben werden, es können also auch Sekundenbruchteile angegeben werden.

Beispiele:

TIME_OF_DAY#15:36:30.123 tod#00:00:00

10-34

CoDeSys V2.3

10 - ANHANG

DATE_AND_TIME-Konstanten, Kombination von Datum und Uhrzeit:

DATE_AND_TIME-Konstanten beginnen mit "dt#", "DT#", "DATE_AND_TIME#" oder "date_and_time#". Nach der Datumsangabe folgt ein Bindestrich und danach die Uhrzeit.

Beispiele:

DATE_AND_TIME#1996-05-06-15:36:30 dt#1972-03-29-00:00:00

10.15 Definierte Datentypen

Array

Es werden ein-, zwei-, und dreidimensionale Felder (Arrays) von elementaren Datentypen unterstützt. Arrays können im Deklarationsteil eines Bausteins und in den globalen Variablenlisten definiert werden.

Syntax:

<Feld_Name>:ARRAY [<ug1>..<og1>,<ug2>..<og2>,<ug3>..<og3>] OF <elem. Typ>.

ug1, ug2, ug3 geben die untere Grenze des Feldbereichs an, og1, og2, og3 die obere Grenze. Die Grenzwerte müssen ganzzahlig sein.

Beispiel:

Kartenspiel : ARRAY [1..13, 1..4] OF INT;

Initialisierung von Arrays:

Beispiele für die komplette Initialisierung eines Arrays:arr1 : ARRAY [1..5] OF INT := 1,2,3,4,5; arr2 : ARRAY [1..2,3..4] OF INT := 1,3(7);

(* kurz für 1,7,7,7 *)

arr3 : ARRAY [1..2,2..3,3..4] OF INT := 2(0),4(4),2,3; (* kurz für 0,0,4,4,4,4,2,3 *)

Beispiel für die Initialisierung eines Arrays einer Struktur:

TYPE STRUCT1 STRUCT

p1:int;

p2:int;

p3:dword;

END_STRUCT

ARRAY[1..3] OF STRUCT1:= (p1:=1,p2:=10,p3:=4723),(p1:=2,p2:=0,p3:=299), (p1:=14,p2:=5,p3:=112);

Beispiel für eine teilweise Initialisierung eines Arrays: arr1 : ARRAY [1..10] OF INT := 1,2;

Elemente, für die kein Wert vorgegeben wird, werden mit dem Default-Initialwert des Basistypen initialisiert. Im obigen Beispiel werden also die Elemente anarray[6] bis anarray[10] mit 0 initialisiert.

Zugriff auf Array-Komponenten:

Auf Komponenten von Arrays greift man bei einem zweidimensionalen Feld mit folgender Syntax zu:

<Feld_Name>[Index1,Index2]

Beispiel:

Kartenspiel[9,2]

CoDeSys V2.3

10-35

Definierte Datentypen

Hinweis: Wenn Sie in Ihrem Projekt eine Funktion mit Namen CheckBounds definieren, können Sie damit Bereichsüberschreitungen bei Arrays automatisch überprüfen!

Funktion Checkbounds

Wenn Sie in Ihrem Projekt eine Funktion mit Namen CheckBounds definieren, können Sie damit Bereichsüberschreitungen in Arrays automatisch überprüfen! Der Name der Funktion ist festgelegt und darf nur diese Bezeichnung besitzen.

Beispiel für die Funktion CheckBounds:

UNCTION CheckBounds : INT VAR_INPUT

index, lower, upper: INT; END_VAR

IF index < lower THEN CheckBounds := lower;

ELSIF index > upper THEN CheckBounds := upper;

ELSE CheckBounds := index; END_IF

Das folgende Beispielprogramm zum Testen der CheckBounds-Funktion greift außerhalb der Grenzen eines definierten Arrays zu. Die Funktion CheckBounds gewährleistet, dass der Wert TRUE nicht an die Stelle A[10], sondern an der oberen noch gültigen Bereichsgrenze A[7] zugewiesen wird. Mit der CheckBounds-Funktion können somit Zugriffe außerhalb von Array-Grenzen korrigiert werden.

Test Programm für die CheckBounds Funktion:

PROGRAM PLC_PRG

VAR

a:ARRAY[0..7] OF BOOL;

b:INT:=10;

END_VAR a[b]:=TRUE;

Pointer

In Pointern speichert man die Adresse von Variablen oder Funktionsblöcken zur Laufzeit eines Programms.

Pointerdeklarationen haben folgende Syntax:

<Bezeichner>: POINTER TO <Datentyp/Funktionsblock>;

Ein Pointer kann auf jeden beliebigen Datentyp und Funktionsblock zeigen, auch selbstdefinierte.

Mit dem Adressoperator ADR wird dem Pointer die Adresse einer Variablen oder Funktionsblocks zugewiesen.

Die Dereferenzierung eines Pointers erfolgt über den Inhaltsoperator "^" nach dem Pointerbezeichner.

Beispiel:

pt:POINTER TO INT; var_int1:INT := 5; var_int2:INT;

pt := ADR(var_int1);

var_int2:= pt^; (* var_int2 ist nun 5 *)

Achtung: Wenn Online Change angewendet wird, können sich Inhalte von Adressen verschieben. Beachten Sie dies bei der Verwendung von Pointern auf Adressen.

Aufzählungstyp, Enumeration

Ein Aufzählungstyp ist ein selbstdefinierter Datentyp, der aus einer Menge von String-Konstanten besteht. Diese Konstanten bezeichnet man als Enumerationswerte.

Die Enumerationswerte sind im ganzen Projekt bekannt, auch wenn Sie lokal in einem Baustein deklariert wurden. Legen Sie ihre Aufzählungstypen am besten als Objekte im Object Organizer unter

10-36

CoDeSys V2.3

10 - ANHANG

der Registerkarte Datentypen an. Sie beginnen mit dem Schlüsselwort TYPE und enden mit END_TYPE.

Syntax:

TYPE <Bezeichner>:(<Enum_0> ,<Enum_1>, ...,<Enum_n>);

END_TYPE

Eine Variable vom Typ <Bezeichner> kann einen der Enumerationswerte annehmen und wird mit dem ersten initialisiert. Die Werte sind zu ganzen Zahlen kompatibel, d.h. man kann damit Operationen wie mit INT durchführen. Der Variablen kann eine Zahl x zugewiesen werden. Sind die Enumerationswerte nicht initialisiert, beginnt die Zählung bei 0. Achten Sie beim Initialisieren darauf, dass die Initialwerte aufsteigend sind. Die Gültigkeit der Zahl wird zur Laufzeit überprüft.

Beispiel:

TYPE AMPEL: (Rot, Gelb, Gruen:=10); (*Rot hat den Initialwert 0, Gelb 1, Gruen 10 *)

END_TYPE

AMPEL1 : AMPEL ;

AMPEL1:=0; (* Ampel hat den Wert Rot*) FOR i:= Rot TO Gruen DO

i := i + 1;

END_FOR;

Der gleiche Enumerationswert darf sowohl innerhalb einer Enumeration wie auch bei der Verwendung verschiedener Enumerationen innerhalb desselben Bausteins nicht zweimal verwendet werden.

Beispiel:

AMPEL: (rot, gelb, gruen); FARBE: (blau, weiss, rot);

Fehler: rot darf nicht für AMPEL und FARBE verwendet werden, wenn diese im gleichen Baustein benützt werden.

Strukturen

Strukturen werden als Objekte (Datentypen) im Object Organizer unter der Registerkarte Datentypen abgelegt. Sie beginnen mit den Schlüsselwörtern TYPE und STRUCT und enden mit END_STRUCT und END_TYPE.

Strukturdeklarationen haben folgende Syntax:

TYPE <Strukturname>:

STRUCT

<Variablendeklaration 1>

.

.

<Variablendeklaration n>

END_STRUCT END_TYPE

<Strukturname> ist nun ein Typ, der im gesamten Projekt bekannt ist, und der wie ein Standard Datentyp benutzt werden kann.

Verschachtelte Strukturen sind erlaubt. Die einzige Einschränkung ist, dass Variablen nicht auf Adressen gesetzt werden können (AT-Deklaration ist nicht erlaubt!).

Beispiel für eine Strukturdefinition Polygonzug:

TYPE Polygonzug:

STRUCT

Start:ARRAY [1..2] OF INT;

Punkt1:ARRAY [1..2] OF INT;

CoDeSys V2.3

10-37

Definierte Datentypen

Punkt2:ARRAY [1..2] OF INT;

Punkt3:ARRAY [1..2] OF INT;

Punkt4:ARRAY [1..2] OF INT;

Ende:ARRAY [1..2] OF INT;

END_STRUCT

END_TYPE

Beispiel für die Initialisierung einer Struktur vom Typ Polygonzug:

Poly_1: Polygonzug := ( Start:=3,3, Punkt1:=5,2, Punkt2:=7,3, Punkt3:=8,5,

Punkt4:=5,7, Ende := 3,5);

Initialisierungen mit Variablen sind nicht möglich. Ein Beispiel für die Initialisierung eines Arrays einer Struktur siehe unter 'Arrays'.

Zugriff auf Strukturen:

Auf Komponenten von Strukturen greift man mit folgender Syntax zu:

<Struktur_Name>.<Komponentenname>

Für das oben genannte Beispiel der Struktur Polygonzug erfolgt der Zugriff auf die Komponente Start dementsprechend über Poly_1.Start

Referenzen

Der selbstdefinierte Datentyp Referenz dient dazu, um einen alternativen Namen (alias) für einen Datentypen oder einen Funktionsblock zu erzeugen.

Legen Sie ihre Referenzen als Objekte im Object Organizer unter der Registerkarte Datentypen an. Sie beginnen mit dem Schlüsselwort TYPE und enden mit END_TYPE.

Syntax:

TYPE <Bezeichner>: <Zuweisungsausdruck>; END_TYPE

Beispiel:

TYPE message:STRING[50];

END_TYPE;

Unterbereichstypen

Ein Unterbereichstyp ist ein Datentyp, dessen Wertebereich nur eine Untermenge eines Basistypen

umfasst. Die Deklaration kann im Registerblatt Datentypen erfolgen, eine Variablen kann aber auch direkt mit einem Unterbereichstypen deklariert werden:

Syntax für die Deklaration im Register 'Datentypen':

TYPE <Name> : <Inttype> (<ug>..<og>) END_TYPE;

<Name>

muss ein gültiger IEC-Bezeichner sein,

<Inttype>

ist einer der Datentypen SINT, USINT, INT, UINT, DINT, UDINT, BYTE, WORD,

 

DWORD (LINT, ULINT, LWORD).

<ug>

ist eine Konstante, die kompatibel sein muss zum Basistypen, und die die Untergrenze

 

des Bereichstypen festlegt. Die Untergrenze selbst gehört zu diesem Bereich.

<og>

ist eine Konstante, die kompatibel sein muss zum Basistypen, und die die Obergrenze

 

des Bereichstypen festlegt. Die Obergrenze selbst gehört zu diesem Basistypen.

Beispiel:

TYPE

SubInt : INT (-4095..4095);

END_TYPE

10-38

CoDeSys V2.3

10 - ANHANG

Direkte Deklaration einer Variablen mit einem Unterbereichstypen

Beachten Sie die korrekte Angabe eines Initialwerts, wenn der Unterbereich nicht die '0' enthält:

VAR

i1 : INT (-4095..4095); i2: INT (5..10):=5;

ui : UINT (0..10000);

END_VAR

Wird einem Unterbereichstypen eine Konstante zugewiesen (in der Deklaration oder in der Implementation), die nicht in diesen Bereich fällt (z.B. i:=5000), wird eine Fehlermeldung ausgegeben.

Um die Einhaltung der Bereichsgrenzen zur Laufzeit zu überprüfen, müssen die Funktionen

CheckRangeSigned bzw. CheckRangeUnsigned eingefügt werden. In diesen können Bereichsverletzungen in geeigneter Art und Weise abgefangen werden (z.B. kann der Wert abgeschnitten werden oder ein Fehlerflag gesetzt werden). Sie werden implizit aufgerufen, sobald auf eine Variable geschrieben wird, die von einem Unterbereichstyp ist, der aus einem vorzeichenbehafteten bzw. vorzeichenlosen Typ gebildet wurde.

Beispiel:

Im Falle einer Variable eines vorzeichenbehafteten Unterbereichstyps (also wie i von oben) wird die Funktion CheckRangeSigned aufgerufen, die folgendermaßen programmiert sein könnte, um einen Wert auf den erlaubten Bereich zurückzuschneiden:

FUNCTION CheckRangeSigned : DINT VAR_INPUT

value, lower, upper: DINT;

END_VAR

IF (value < lower) THEN

CheckRangeSigned := lower; ELSIF(value > upper) THEN

CheckRangeSigned := upper; ELSE

CheckRangeSigned := value;

END_IF

Zwingend für einen automatischen Aufruf ist der Funktionsname CheckRangeSigned und die Gestaltung der Schnittstelle: Rückgabewert und drei Parameter vom Typ DINT.

Die Funktion wird beim Aufruf folgendermaßen parametriert:

-value: bekommt den Wert, der dem Bereichstypen zugewiesen werden soll

-lower: die Untergrenze des Bereichs

-upper: die Obergrenze des Bereichs

-Return value: der Wert, der tatsächlich dem Bereichstypen zugewiesen wird Aus einer Zuweisung i := 10*y; wird in diesem Beispiel implizit folgende erzeugt:

i:= CheckRangeSigned(10*y, -4095, 4095);

Wenn y beispielsweise den Wert 1000 hat, dann hat i nach dieser Zuweisung trotzdem nur den Wert 4095.

Entsprechend gilt für die Funktion CheckRangeUnsigned: Funktionsname und Schnittstelle müssen korrekt sein:

FUNCTION CheckRangeUnsigned : UDINT

VAR_INPUT

CoDeSys V2.3

10-39

Definierte Datentypen

value, lower, upper: UDINT; END_VAR

Achtung: Sind die beiden Funktionen CheckRangeSigned und CheckRangeUnsigned nicht vorhanden, findet zur Laufzeit keine Typüberprüfung der Unterbereichstypen statt! Die Variable i könnte dann also durchaus beliebige Werte zwischen –32768 und 32767 annehmen!

Achtung: Wenn eine Funktion CheckRangeSigned bzw. CheckRangeUnsigned wie oben gezeigt implementiert ist, kann bei der Verwendung des Unterbereichstypen in einer FOR-Schleife eine Endlosschleife entstehen. Dies geschieht genau dann, wenn der für die FOR-Schleife angegebenen Bereich genauso groß oder größer ist als der des Unterbereichstypen !

Beispiel:

VAR

ui : UINT (0..10000);

END_VAR

FOR ui:=0 TO 10000 DO

...

END_FOR

Die FOR-Schleife wird nicht verlassen, da ui nicht größer als 10000 werden kann.

Ebenso ist der Inhalt der CheckRange-Funktionen bei der Verwendung von Inkrementationswerten in der FORSchleife zu beachten !

10-40

CoDeSys V2.3

Соседние файлы в папке 759-333