Zuviel Werbung? - > Hier kostenlos beim SPS-Forum registrieren

Seite 1 von 3 123 LetzteLetzte
Ergebnis 1 bis 10 von 28

Thema: DB nach Werten durchsuchen und Adresse des Eintrags herausfinden

  1. #1
    Registriert seit
    05.11.2011
    Beiträge
    75
    Danke
    0
    Erhielt 0 Danke für 0 Beiträge

    Standard


    Zuviel Werbung?
    -> Hier kostenlos registrieren
    Hallo,

    ich habe eigentlich schon eine Funktion gefunden, welche die Aufgabenstellung lösen kann - der FC86 (TBL_Find). Allerdings benötigt dieser FC86 die Quellangabe als TYP Pointer (kein ANY!), welche ich aber nicht durch einen übergeordneren FC/FB durchreichen kann.

    Ich hoffe nun, eine vergleichbare Funktion zu finden - welche dann aber variabel mit einem normalen ANY-Pointer (damit sollte es zumindest dann gehen?!) angesteuert werden kann.



    Konkret:
    Ich muss einen DB nach bestimmten Werten durchsuchen und dessen Position im DB herausfinden. Diese in sich dann geschlossene "Suchfunktion" soll wiederum in einem überlagerten FC/FB aufgerufen werden. Dem überlagerten FC/FB werden dann die variablen Daten (DB, welcher durchsucht werden soll, Suchmuster, ...) übergeben und an den FC86 durchgereicht.
    Das Problem mit dem FC86 ist, dass der Pointer (TYP Pointer, kein Typ ANY) vom überlagerten FC/FB nicht an den FC86 übergeben werden kann - der FC86 braucht wie gesagt die Suchquelle als Typ POINTER...


    Die Funktion sollte sowohl Int als auch ggf. STRING suchen bzw finden können.
    Geändert von saarlaender (15.06.2012 um 13:43 Uhr)
    Zitieren Zitieren DB nach Werten durchsuchen und Adresse des Eintrags herausfinden  

  2. #2
    Registriert seit
    02.02.2012
    Ort
    Kaarst
    Beiträge
    126
    Danke
    10
    Erhielt 7 Danke für 7 Beiträge

    Standard

    Wie wärs wenn du dir den Zeiger im Programm einfach anhand der vorgaben am übergeordneten baustein zusammen baust?

    Paar sprünge, paar multiplikatoren, fertig! ...

  3. #3
    Registriert seit
    06.10.2009
    Ort
    NRW
    Beiträge
    1.569
    Danke
    63
    Erhielt 258 Danke für 218 Beiträge

    Standard

    Ich würde das mit einer Schleife lösen.

    Die DB-Länge auslesen und damit die Anzahl der Schleifendurchläufe vorbelegen.
    In der Schleife den Vergleich mit dem gewünschten Wert machen und bei einem Treffer den Schleifenzähler auswerten um die Adresse des Wertes auszulesen.
    Meine Motivation läuft nackig mit einem Cocktail über eine Wiese.

  4. #4
    Registriert seit
    27.05.2004
    Ort
    Thüringen/Berlin
    Beiträge
    12.220
    Danke
    533
    Erhielt 2.696 Danke für 1.948 Beiträge

    Standard

    Wenn man das universell machen wollte, also jeden beliebigen DB durchsuchbar, nach einem beliebigen String oder einer Int, dann muß man den DB byteweise nach dem ersten Byte der Int oder des String durchsuchen, bei Treffern den Rest der Int oder des String vergleichen und ggf. das Ergebnis melden. Dann ist noch die Frage, meldet man den ersten Treffer, alle Treffer oder den jeweils nächsten Treffer? Hat man große DB kann man das u.U. nicht mit einer einzigen Schleife machen, da dann die Zykluszeit vielleicht zu stark steigt. In diesem Falle muß man das auch noch auf mehrere Zyklen aufteilen.

    Etwas Anderes ist es dann schon, wenn der zu durchsuchende DB bereits eine feste Struktur hat, also z.Bsp. 50 Einträge, mit je einer Int und einem String. Dann kann man tatsächlich diese jeweils 50 festen Einträge per Schleife durchsuchen, vergleichen und die Fundstellen melden. Das geht recht einfach in SCL, aber auch in AWL kann man das noch lösen, dann aber mit indirekter Adressierung.

    Fall 2 ist sicher schneller zu programmieren, als Fall 1.
    Gruß
    Ralle

    ... there\'re 10 kinds of people ... those who understand binaries and those who don\'t …
    and the third kinds of people … those who love TIA-Portal

  5. #5
    Registriert seit
    05.11.2011
    Beiträge
    75
    Danke
    0
    Erhielt 0 Danke für 0 Beiträge

    Standard

    Also erstmal danke für die Antworten.

    Ich suche allerdings eine bzw. ggf. mehrere fertige Funktionen, die diese Aufgabe so oder so ähnlich erfüllen können. Die eine, welche ich gefunden hab (TBL_Find) eignet sich wie gesagt ja leider nicht für den dynamischen Einbau in einem überlagerten FC/FB.


    Gibts da andere fertige Funktionen von Siemens, der OpenSource-Collection oder ggf. sogar kostenpflichtige?
    Ich fand mal irgendwo eine String-Find-Funktion, verwarf die aber da ich direkt im Anschluss die Table-Find-Funktion fand. Kann mir da evt. jmd. auf die Sprünge helfen?


    Sofern es außer TBL_Find nichts weiteres gibt: Ist jemand in der Lage, so etwas in AWL/SCL -bezahlbar- zu programmieren?



    ps: Der zu suchende bzw. zu findende String/INT/...-Wert wird nur einmal im DB vorkommen, dafür sorgt das Leitsystem.
    Es soll eine Ident-Nummer gesucht werden und anschließend über dessen Position im DB die im dazugehörigen UDT liegenden Infos abgefragt werden.


    BSP:

    UDT:
    > Ident-NR (INT/String)
    >> Aktion-1 (INT)
    >> Aktion-2 (INT)
    >> Aktion-3 (INT)

    Ich suche eine Ident-Nr, bekomme über die Funktion die entspr. Position im DB zurück und kann dann durch das Offset schauen, welcher Wert zur Aktion-1, Aktion-2 oder Aktion-X gehört.
    Geändert von saarlaender (18.06.2012 um 11:43 Uhr)

  6. #6
    Registriert seit
    29.03.2004
    Beiträge
    5.731
    Danke
    143
    Erhielt 1.685 Danke für 1.225 Beiträge

    Standard

    Ich bin kein Freund von Any-Pointer Gebastel wenn man in SCL programmiert.
    Wenn man die Quellen hat setze ich am liebsten eine konstante Array-Größe an allen Stellen wo es vorkommt ein.
    Als Basis könnte dir der Codeschnipsel dienen. Für andere Datentypen muss man einfach den Datentyp des Arrays und des Suchmusters ändern.
    Code:
    FUNCTION FC100 : VOID
    
    CONST
        ANZ := 10;                    // Größe des Arrays
    END_CONST
        
    VAR_INPUT
        data : ARRAY[1..ANZ] OF INT;  // zu durchsuchendes Array
        ptrn : INT;                   // zu suchende Zahl
    END_VAR
    
    VAR_OUTPUT
        pos : INT;                    // Position, wenn nicht gefunden dann -1
    END_VAR
    
    VAR_TEMP
        i : INT;
    END_VAR   
       
    BEGIN
        pos := -1;
        FOR i := 1 TO ANZ DO
            IF data[i] = ptrn THEN
                pos := i;
                EXIT;
            END_IF;
        END_FOR;
    END_FUNCTION

  7. #7
    Registriert seit
    02.02.2012
    Ort
    Kaarst
    Beiträge
    126
    Danke
    10
    Erhielt 7 Danke für 7 Beiträge

    Standard

    Ihr habt alle zu viel speicher in euren SPS'n ...

    War am Wochenende schon kurz davor nen universalbaustein zu basteln, einfach weils mir in den fingern juckte!
    Ist bisschen tricky aber auch in awl realisierbar ... hätte ich lust drauf.

    Könnte dir anbieten dir da was zu schreiben bis ende nächster woche (bin jetzt erstmal viel unterwegs).

    Schreib dann aber bitte noch mal detailiert WAS du suchen willst oder ob du einen baustein haben willst der alles suchen kann (INT/WORD/REAL/CHAR/STRING).
    Wobei ich immernoch net raffe wieso man auf die idee kommt nen string oder char's in ner sps zu speichern ...

  8. #8
    Registriert seit
    29.03.2004
    Beiträge
    5.731
    Danke
    143
    Erhielt 1.685 Danke für 1.225 Beiträge

    Standard

    Zitat Zitat von martin1988 Beitrag anzeigen
    Ihr habt alle zu viel speicher in euren SPS'n ...
    Du redest von dir, oder wen meinst du?
    Ein Universalbaustein muss doch die Auswertung für alle Datentypen mitschleppen, auch wenn sie im konkreten Programm gar nicht benötigt werden.

    Und wenn du noch nie einen String oder Char in der SPS speichern musstest ist es kein Wunder dass du bisher mit AWL auskamst.

  9. #9
    Registriert seit
    17.06.2004
    Ort
    Offenau
    Beiträge
    3.745
    Danke
    209
    Erhielt 421 Danke für 338 Beiträge

    Standard

    Ich hab mir dazu auch schon mal einen Baustein geschrieben...

    Der sucht aber eher in einer bestimmten Struktur, vielleicht hilfts ja...

    Code:
    FUNCTION FC 124 : VOIDTITLE =STD_ANY_SUCHEN
    //===================================================
    //Technische Daten:
    //====================================================
    //           Version: 1.00
    //             Datum: 25.09.2009
    //====================================================
    //             Autor: Kühner J.
    //Baustein Name Symb: STD_ANY_SUCHEN
    //
    //====================================================
    //Beschreibung:
    //
    //Such nach einem gegebenen ANY in einem DB.
    //
    //Dazu kann die Struct größe in der Sich der Any befindet,
    //der DB, und die Startadresse eingegeben werden.
    //Die Any Länge wird aus den zu suchenden Daten ausgelesen.
    //
    //Der FC gibt 0 zurück wenn nichts gefunden wurde und >0
    //die Nummer des Structes!
    //====================================================
    VERSION : 0.1
    
    
    
    
    VAR_INPUT
      VERGLEICHS_ANY : ANY ;    //Any zu den Daten die Verglichenwerden sollen (Bsp. der gescannte Barcode)
      DB_VERGLEICH : INT ;    //DB in dem die Daten stehen
      GROESE_STRUCT_VERGLEICH : INT ;    //Größse des zu durchlaufenden Structes
      ANZAHL_VERGLEICH : INT ;    //Anzahl der Struct Elemente
      START_VERGLEICH : INT ;    //Adresse im STruct
    END_VAR
    VAR_OUTPUT
      ZAEHLER_AUSGABE : INT ;    //Nummer des Datensatzes, 0 = keinen gefunden!
    END_VAR
    VAR_TEMP
      ANY1 : ANY ;    
      ANY2 : ANY ;    
      ZAEHLER_1 : INT ;    
      ZAEHLER_2 : INT ;    
      RET_VAL_INT : INT ;    
      LAENGE_ANY : INT ;    
      STARTADRESSE_IN_LOKALDAT : INT ;    
      DATEN : ARRAY  [1 .. 100 ] OF BYTE ;    
    END_VAR
    BEGIN
    NETWORK
    TITLE =
    
    
          L     0; 
          T     #ZAEHLER_AUSGABE; 
          T     #ZAEHLER_1; 
    
    
    //Startadresse der Temporär in den Lokaldaten abgelegten Daten!
          L     30; 
          T     #STARTADRESSE_IN_LOKALDAT; 
    
    
    //Vergleichsdaten in Lokaldaten kopieren
    //ANY 1 auf Vergleichsdaten nutzen
          L     P##VERGLEICHS_ANY; 
          LAR1  ; 
          L     D [AR1,P#0.0]; 
          T     LD     0; 
          L     D [AR1,P#4.0]; 
          T     LD     4; 
          L     W [AR1,P#8.0]; 
          T     LW     8; 
    
    
    //ANY 2 auf Lokaldaten befüllen
          L     28; 
    
    
          L     W#16#1002; //Typ BYTE
          T     LW    10; 
          L     LW     2; //Anzahl Bytes
          T     LW    12; 
          T     #LAENGE_ANY; 
          L     0; //Quell-DB
          T     LW    14; 
          L     #STARTADRESSE_IN_LOKALDAT; //Startadresse in Lokaldaten
          SLD   3; 
          OD    DW#16#87000000; //87 Vorgänger-Lokaldatenbereich
          T     LD    16; 
    
    
          CALL SFC   20 (
               SRCBLK                   := #ANY1,
               RET_VAL                  := #RET_VAL_INT,
               DSTBLK                   := #ANY2);
    
    
    
    
    sl1:  L     #ZAEHLER_1; 
          +     1; 
          T     #ZAEHLER_1; 
          L     #ANZAHL_VERGLEICH; 
          >I    ; 
          BEB   ; 
    
    
          L     #ZAEHLER_1; 
          +     -1; 
          L     #GROESE_STRUCT_VERGLEICH; 
          *D    ; 
          L     #START_VERGLEICH; 
          +D    ; 
          SLD   3; 
          LAR1  ; 
    
    
          L     #STARTADRESSE_IN_LOKALDAT; 
          SLD   3; 
          LAR2  ; 
    
    
          L     0; 
    sl2:  T     #ZAEHLER_2; 
    
    
          L     DBB [AR1,P#0.0]; 
          L     LB [AR2,P#0.0]; 
          <>I   ; 
          SPB   sl1; //ungleich, weiter springen!
    
    
          L     P#1.0; 
          +AR1  ; 
          +AR2  ; 
    
    
          L     #LAENGE_ANY; 
          +     -2; 
          L     #ZAEHLER_2; 
          <=I   ; 
          SPB   gl; 
    
    
          +     1; 
          SPA   sl2; 
    
    
    //ergebnis ist gleich
    gl:   L     #ZAEHLER_1; 
          T     #ZAEHLER_AUSGABE; 
    END_FUNCTION

    P.S. : Das umkopieren der Vergleichsdaten hätte Ich mir womöglich sparen können! Warum Ich das gemacht hab? Weiss nimmer...
    Geändert von Jochen Kühner (18.06.2012 um 17:01 Uhr)
    ---------------------------------------------
    Jochen Kühner
    https://github.com/jogibear9988/DotN...ToolBoxLibrary - Bibliothek zur Kommunikation mit PLCs und zum öffnen von Step 5/7 Projekten

  10. #10
    Registriert seit
    02.02.2012
    Ort
    Kaarst
    Beiträge
    126
    Danke
    10
    Erhielt 7 Danke für 7 Beiträge

    Standard


    Zuviel Werbung?
    -> Hier kostenlos registrieren
    Zitat Zitat von Thomas_v2.1 Beitrag anzeigen
    Du redest von dir, oder wen meinst du?
    Ein Universalbaustein muss doch die Auswertung für alle Datentypen mitschleppen, auch wenn sie im konkreten Programm gar nicht benötigt werden.

    Und wenn du noch nie einen String oder Char in der SPS speichern musstest ist es kein Wunder dass du bisher mit AWL auskamst.
    ;D
    Ich weiß noch nicht wo ich lande, aber ich denke ich bleibe unter 1k!
    Das man mit SCL auch vieles einfach hinbekommt ist klar, zumindest so lang man die quelle hat!
    Aber ein übersetztes SCL programm ist immer größer wie das selbe in AWL direkt geschrieben ...

    Aber bitte geb mir ein beispiel wo es NOTWENDIG ist mit chars und strings in ner cpu zu arbeiten! (abgesehen von irgendwelchen kranken kundenvorstellungen)
    Das man mit ner CPU viel spielen kann ist mir klar aber ich hab schon viele Zeilen programm geschrieben und noch viel mehr kranken scheiss gesehen und dabei war nix was mit chars oder strings arbeitete ...
    Aber ich lass mich gern eines besseren belehren!
    Also nur her damit

Ähnliche Themen

  1. Antworten: 7
    Letzter Beitrag: 03.12.2011, 01:05
  2. DB nach Werten durchsuchen - SCL ?
    Von karsten.schmidt im Forum Simatic
    Antworten: 2
    Letzter Beitrag: 26.03.2011, 13:15
  3. DINT nach INT bei positiven und ganzzahligen Werten (Frequenzmessung)
    Von poppycock im Forum Programmierstrategien
    Antworten: 9
    Letzter Beitrag: 23.07.2009, 21:28
  4. Antworten: 5
    Letzter Beitrag: 02.07.2007, 23:07
  5. Adresse herausfinden
    Von Knoll im Forum Simatic
    Antworten: 3
    Letzter Beitrag: 07.09.2006, 10:02

Lesezeichen

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •