Zum Thema Pointer

1schilcher

Level-1
Beiträge
137
Reaktionspunkte
2
Zuviel Werbung?
-> Hier kostenlos registrieren
Machen gerade im SPS Kurs die indirekte Adressierung und somit verbunden auch die ganzen Pointer Arten. Wie das ganze funktioniert ist mir jetzt so ungefähr zu 90 Prozent klar. Aber für was brauch ich das.
Beispiel:
L 30
SLD 3
LAR1
L MW [AR1,P#0.0]

Somit würde er das MW 30 laden, warum muß ich es so kompliziert schreiben, ich kann doch gleich schreiben - L MW30, oder geht es da rein um Speicher in der CPU zu sparen.
 
:ROFLMAO: Du bist gut ;)

Nimm an, du hast als Fehlermeldungen Bitmeldungen, die in einem DB "Störmeldungen" eingetragen werden (So wird as bei ProTool und WinCCFlex gemacht).

Nun willst du einen FC oder FB schreiben, der abfragt, ob Fehlermeldungen anliegen.

Du könntest alle Bits abfragen (Bei 496 Störmelfungen nicht schön).
Du könntest nun lauter Wortvergleicher auf Null schreiben, verodern und schon hättest du das Ergebnis. (Macht auch noch Arbeit, bei 32 Worten.)

Oder eine Schleife Programmieren:

Code:
      AUF   "STOERMELDUNGEN DB"

      L     P#0.0
      T     #pointer_1

      L     0
      T     #ergebnis

      L     32                          //Anzahl Störmeldungen (Wortweise)
SC02: T     #zaehler

      L     DBW [#pointer_1]            // Lade Datenwort
      L     0                           // Lade 0
      ==I                               // keine Störmeldung !!!
      SPB   NUL2                        // Ergebnis nicht hochzählen
      L     #ergebnis                   // bei Erg <> 0 Ergebnis hochzählen
      L     1                           // um 1 erhöhen
      +I    
      T     #ergebnis

NUL2: NOP   0                           // Zeiger erhöhen aud nächstest DW
      L     #pointer_1
      L     P#2.0
      +D    
      T     #pointer_1
      L     #zaehler
      LOOP  SC02                        // Schleife solange, bis #zaehler auf 0

      L     #ergebnis                   // bei Ergebnis <> 0 liegt Fehler vor
      L     0
      <>I   
      =     "M1.0 Sammelfehler"
Ist hier nur etwas anders geschrieben:

L 0
SLD 3
LAR1
L MW [AR1,P#0.0]

man kann auch gleich einen Pointer laden und damit arbeiten, wie oben beschrieben, aber das Prinzip ist das Selbe.

L P0.0
T #Pointer_1 //das ist ein DWORD
L MW [#Pointer_1]
 
Zuletzt bearbeitet:
Zuviel Werbung?
-> Hier kostenlos registrieren
:ROFLMAO: Du bist gut ;)

Du könntest nun lauter Wortvergleicher auf Null schreiben, verodern und schon hättest du das Ergebnis. (Macht auch noch Arbeit, bei 32 Worten.)
Warum denn Wort- und nicht DWort-Vergleicher?
Warum erst vergleichen und dann verodern?
A DBxx
L DBD 0
L DBD 4
OD
L DBD 8
OD
L DBD 12
OD
L DBD 16
L 0
><D
...
ist kaum mehr zu Schreiben (ok, ich habe es nur für bis zu 160 Meldungen hingeschrieben), weniger fehlerträchtig und schneller.


Nun etwas, wozu Pointer wirklich gut sind:
Du hast einen runden liegenden Tank mit Füllstandsmessung. Die gibt dir die Höhe und du willst die Liter wissen. Rechnen ist schlecht, weil schon in der Fläche des Kreissegments lauter sin, arcsin, und sqrt vorkommen und wenn der Tank dann noch gewölbte Seitenteile hat...
Deshalb gibt es vom Hersteller eine Peiltabelle, Liter bei x cm. Die tippst du in einen DB ab, z.B. für jeden ganzen Zentimeter einen Wert. Nun "errechnest" du aus der Höhe, in welchem Datenwort deine Liter stehen. Und auf das errechnete Datenwort kannst du nur mit einem Pointer zugreifen, weil ja beim Programmieren nicht feststeht, wie hoch das Zeug im Tank steht.
 
30 muss ja keine konstante sein, sinn macht das ganze wenn es ebenfalls eine variable ist und du abhähning von dem was da drin steht auf verschiedene adressen zugreifen kannst...

ohne das funktioniert in einem anständigen sps programm garnix mehr...

nur ein hinweis, nicht falsch verstehen - kein ansticheln zum glaubenskrieg - nur ein hinweis:

in kop und fup geht das nicht nur in awl und scl...


//edit
naja ich bin einfach zu langsam für dieses forum...
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Weil es 1. ein Beispiel ist und es 2. auch Anlagen mit 1500 Fehlermeldungen gibt.

welcher kunde kauft eine anlage mit so vielen störungen?
*duckundweg*


@schilcher

schau mal in der faq oder fütter die sucher hier im forum, das thema wird immer wieder sehr ausführlich diskutiert - darüber findest du ne menge...
 
nur ein hinweis, nicht falsch verstehen - kein ansticheln zum glaubenskrieg - nur ein hinweis:

in kop und fup geht das nicht nur in awl und scl...

Das mag für Siemens und Codesys und sonstige Pseudo-Kop Software gelten, mit "richtiger" Kop Software geht das natürlich. Vielleicht solltet Ihr mal über Euren Siemens Tellerrand rausschauen, dann bemerkt Ihr vielleicht endlich mal was Euch entgeht und wie so manches anderswo einfacher geht.
:ROFLMAO:
 
du redest jetzt von ab?
das stimmt - wobei da früher eben nur kop ging...
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo zusammen,

muss auch mal meinen Senf zu der Sammelstörungsgeschichte dazugeben.

Ich würde auch die Version von Ralle verwenden, da sie -einmal angelegt- sehr einfach auf einen veränderten Meldebereich angepasst werden kann.

Ausserdem ist mit der LOOP-Variante, gerade bei großen Meldebereichen, Zeitersparnis für die SPS drin.

Wenn man nämlich nur die Sammelstörung auswerten will sollte das Prog. die Schleife beim ersten gefundenen Fehler verlassen:

.
.
.
L DBW [#pointer_1] // Lade Datenwort
L 0 // Lade 0
<>I // Störmeldung !!!
SPB ERR
L #pointer_1
L P#2.0
+D
T #pointer_1
L #zaehler
LOOP SC02
CLR
ERR: = "M1.0 Sammelfehler"

Damit erspart man sich weitere Vergleiche wenn das Ergebnis eh schon feststeht.

Schöne Grüße

Micha
 
Warum denn Wort- und nicht DWort-Vergleicher?
Warum erst vergleichen und dann verodern?
A DBxx
L DBD 0
L DBD 4
OD
L DBD 8
OD
L DBD 12
OD
L DBD 16
L 0
><D
...
ist kaum mehr zu Schreiben (ok, ich habe es nur für bis zu 160 Meldungen hingeschrieben), weniger fehlerträchtig und schneller.


Nun etwas, wozu Pointer wirklich gut sind:
Du hast einen runden liegenden Tank mit Füllstandsmessung. Die gibt dir die Höhe und du willst die Liter wissen. Rechnen ist schlecht, weil schon in der Fläche des Kreissegments lauter sin, arcsin, und sqrt vorkommen und wenn der Tank dann noch gewölbte Seitenteile hat...
Deshalb gibt es vom Hersteller eine Peiltabelle, Liter bei x cm. Die tippst du in einen DB ab, z.B. für jeden ganzen Zentimeter einen Wert. Nun "errechnest" du aus der Höhe, in welchem Datenwort deine Liter stehen. Und auf das errechnete Datenwort kannst du nur mit einem Pointer zugreifen, weil ja beim Programmieren nicht feststeht, wie hoch das Zeug im Tank steht.

@Zottel: Das kann man auch sehr elegant mit dem S7 Standardbaustein ...(fällt mir gerade nicht ein) "korrelierte Datentabellen" lösen.
Man übergibt dem Funktionsbaustein einen X-Wert und er ermittelt den dazu gehörenden Y-Wert.
Die X- und Y-Wertepaare muß man vorher in einem Datenbaustein hinterlegen. Ist ein feiner Funktionsbaustein der mir schon manches mal
sehr geholfen hat...

Gruß
 
Danke an Alle

Wiedermal ein großes Lob an alle, jetzt ist mir klar für was ich das später mal einsetzen kann. DANKE,
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Es ist wie immer bei Siemens- es gibt mindestens 527 verschiedene Wege, um ans Ziel zu kommen ;)

Noch was zum KOP:
Die Amis und Japaner scheinen eher auf dem KOP- Trip zu sein. Bei denen geht aber auch alles in KOP. Teilweise eben auch nur in KOP. Allen Bradley kenne ich leider (noch) nicht, aber Mitsubishi und Fanuc zum Beispiel sind hauptsächlich (bzw. ausschließlich) mit KOP zu programmieren, und denen ihre Funktionen gehen dann auch alle in KOP. Fanuc kann man auch in Mnenomic (hab' ich's richtig geschrieben?) programmieren, also eine Art AWL, aber da krampft man sich dann einen ab und so weit ich mich entsinne, muss man das vorher auch wieder in KOP rückübersetzen.
Auf der anderen Seite: Der Siemens- Lösungsansatz ist eben offener. Und ich finde, in AWL kann man richtig schön schnell arbeiten, statt Linien zu malen. Und man kann schön dran lang lesen:
U Arbeit fertig
U Nachmittag
U keine Lust mehr
S Feierabend

Gruß, Tobias
 
@Zottel: Das kann man auch sehr elegant mit dem S7 Standardbaustein ...(fällt mir gerade nicht ein) "korrelierte Datentabellen" lösen.
Man übergibt dem Funktionsbaustein einen X-Wert und er ermittelt den dazu gehörenden Y-Wert.
Die X- und Y-Wertepaare muß man vorher in einem Datenbaustein hinterlegen. Ist ein feiner Funktionsbaustein der mir schon manches mal
sehr geholfen hat...

Gruß
Das mag wohl sein, aber ich habe keine Lösung zu einem Problem sondern ein (fast) nur mit Pointern lösbares Problem gesucht. Und ein Standard-Funktionsbaustein ist eine Blackbox und bevor der Frager das mit den Pointern nicht verstanden hat, kann er annehmen, daß innendrin eine Zauberei passiert, die nur Siemens kann.
 
Weil es 1. ein Beispiel ist und es 2. auch Anlagen mit 1500 Fehlermeldungen gibt.
Moment, ich habe nicht gesagt, daß es nicht ab einem gewissen Umfang sinnvoll ist, eine Schleife und Pointer zu verwenden.

Und meine Fragen:
Warum denn Wort- und nicht DWort-Vergleicher?
Warum erst vergleichen und dann verodern?
beziehen sich auf die AWL-Alternative, weil du der Pointer-Lösung übermäßig kompliziertes AWL gegenübergestellt hast:
Warum denn DWort- und nicht Wort-Vergleicher? Weil die CPU es kann und es nur die Hälfte der Anweisungen braucht.
Warum erst verodern und dann vergleichen? Weil du statt n Vergleichen und n Oder-Verknüpfungen nur 1 Vergleich und n Oder-Verknüpfungen hast.
Durch beides zusammen sinkt der Umfang auf ein Viertel.

Ebenso kann man natürlich in Michas Variante mit der Hälfte Schleifendurchläufe auskommen:
Code:
L DBD [#pointer_1] // Lade Datenwort
 L 0 // Lade 0
 <>D // Störmeldung !!!
 SPB ERR
 L #pointer_1
 L P#4.0
 +D 
...
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Frage an "Zottel"

Hallo Zottel, habe mich mit deinem Beispiel (runden liegenden Tank) beschäftigt, und es mal ausprobiert. Mit Pointern ist mir nicht sehr viel eingefallen - ich habe es mal mit meiner Erfahrung gelöst. Meine Lösung sieht so aus:

L MW0 //Wert der Tankhöhe in cm
L 0
==I
SPB wer0
L MW0
L 1
==I
SPB wer1
L MW0
L 2
SPB wer2
usw.

wer0: AUF DB1 //Wertetabelle des Herstellers
L DBW0
T DB2.DBW0 //Dort stehen meine Liter vom Tank
BEA

wer1: Auf DB1
L DBW2
T DB2.DBW0
BEA

wer2: AUF DB1
L DBW4
T DB2.DBW0
BEA

So sieht meine Lösung aus, die auch funktioniert - das ist aber eine einfache Vergleicherlösung - wie würde das, so wie du gesagt hast mit Pointern funktionieren - gib mir mal einen Denkanstoss - DANKE
 
Ja, so geht das auch. Für einen Tank von 1,50m Höhe und einer Auflösung von 1 cm sind es halt 150 Vergleiche. Damit hätte man nach Ralles Art dann auch 150*32 =4800 Fehlermeldungen bearbeiten können...
Mit Pointer (nicht getestet):
Code:
A DBxx    
L MW0 //Wert der Tankhöhe in cm
L P#4.0 // Länge eines DBD der Peiltabelle
*D
T #pointer_1
L DBD [#pointer_1] // Lade Datendoppelwort
Vorraussetzungen:
- Die Peiltabelle steht in einem Datenbaustein ab DBD0. Die Einträge sind
- Doppelworte (z.B. vom Datentyp REAL für krumme Literzahlen).
- Es ist sichergestellt, daß im MW0 kein größerer Wet stehen kann, als der Tabellen-DB Einträge hat, sonst gibt es einen Fehler.
 
Vielen Dank an Alle

Vielen Dank, speziell an "Zottel". Ich habe es ausprobiert - funct 1A!
Ich habe somit das Problem mit 7 Zeilen in einem NW gelöst. Mit meinen Vergleichern wären es ein bisschen mehr geworden - Nochmals DANKE an alle!
 
Zuviel Werbung?
-> Hier kostenlos registrieren
durch SPP statt SPB kann man die L 0 und <>D Anweisung auch noch sparen (wenn ich nicht irre)

Code:
LOOP: L DBD [#pointer_1] // Lade Datenwort
// L 0 // Lade 0
// <>D // Störmeldung !!!
// SPB ERR
 SPP ERR
 L #pointer_1
 L P#4.0
 +D 
...
 
Zurück
Oben