Shabutaro Geschrieben 21. Juni 2011 Geschrieben 21. Juni 2011 Hi, ich absolviere gerade ein Praktikum in einer IT Firma um zu gucken ob sie mich als Azubi übernehmen wollen. Ich habe nun die Aufgabe bekommen aus den Logfiles des Servers Zahlen herrauszulesen und daraus ein Balkendiagram zu plotten. Das Diagram ist kein Problem, nur habe ich keine Ahnung und finde auch im Internet nichts was mir weiterhilft um Zahlen aus einer externen Datei einzulesen, in eine Liste zu packen und diese dann ins Diagram übertragen. Ich kriege es nur hin, indem ich bestimmte Zahlen aus den Logfiles definiere und dann die variable einzeln in die Liste packe. Ich hoffe ihr versteht mein Problem und könnt mir ein bisschen helfen, da ich echt gerne hier meine Ausbildung machen würde und eine guten Eindruck hinterlassen will, indem ich mir vieles selbst beibringe und nicht jede Kleinigkeit nachfragen muss. LG Shabu Zitieren
Shogoki Geschrieben 21. Juni 2011 Geschrieben 21. Juni 2011 Hallo Shabutaro, Um dir helfen zu können, müsste man etwas mehr wissen. Um was für Zahlen handelt es sich, die du auslesen willst? Und wie ist das Logfile strukturiert? Auch ist nur aus deinem Titel ersichtlich, dass du dass Skript in Phyton realisieren möchtest/musst. Mit freundlichen Grüßen Shogoki Zitieren
Shabutaro Geschrieben 21. Juni 2011 Autor Geschrieben 21. Juni 2011 Sobald ich zu hause bin kann ich das genauer erklären Bin noch am arbeiten ^^ Zitieren
Shabutaro Geschrieben 21. Juni 2011 Autor Geschrieben 21. Juni 2011 Ok geht doch jetz, da MIttagspause Um was für Zahlen handelt es sich, die du auslesen willst? Und wie ist das Logfile strukturiert? 1"time","usr","sys","idl","wai","hiq","siq","read","writ","recv","send","in","out","int","csw","used","buff","cach","free""writ" 120-06 03:36:11,1.345,0.606,97.485,0.282,0.052,0.230,3293073.982,4023847.436,0.0,0.0,80.507,740.291,2068.439,6926.836,1093025792.0,317419520.0,447164416.0,6503153664.04023847.436 Das ist eine Zeile, aber ich soll erstmal nur aus 30 Zeilen 1 Wert auslesen, und zwar den rechts neben der Zeit. Alles andere soll ignoriert werden! "Dstat 0.7.2svn CSV output"; "time";"writ" 20-06 03:36:11;4023847.436 20-06 03:36:12;50999296.0 . . . und diese Zahlen sollen dann halt in ein Diagram rein (hoffe das Hilft jetzt mehr) Shabu Zitieren
Shogoki Geschrieben 21. Juni 2011 Geschrieben 21. Juni 2011 Ja, Das ist doch schonmal etwas detailierter. Also Die zweite Code-Box hab ich nicht ganz verstanden... Du hast aber immernoch nicht genau gesagt ob es unbedingt Python sein muss. Also Ich bin kein Python-Spezialist. Aber erstmal allgemein: Du hast wohl ein CSV-File vor dir liegen. Sprich ein Textfile in dem mit kommagetrennte werte stehen. du willst nur einen davon haben nämlich den 2. (Index 1) Im allgemeinen wird das wohl in den meisten Skriptsprachen gleich gelöst: - Zeilenweises einlesen der Textdatei - splitten des Strings anhand des Delimiters "," in ein Array(Funktion heißt häufig split) - ausgeben/weiterverarbeiten des gewünschten Wertes (in diesem Fall wohl Index 1 des Arrays) Das könnte in Perl z.B. so aussehen. Perl-Beispiel: open(LOG,"<server.log"); while(<LOG>) { @array = split($_,","); print $array[1]; } close(LOG);[/PHP] In Python sollte es von der Logik genauso gehen. Das könnte dann in etwa so aussehen (Keine Garantie auf korrekten Code!) [code]for line in open('myfile','r').readlines(): array = split(line, ",") print array[1][/code] Zitieren
flashpixx Geschrieben 21. Juni 2011 Geschrieben 21. Juni 2011 Wenn man mal die Python Dokumentation durchschaut, dann wird man da auch fündig: 5. Built-in Types — Python v2.7.2 documentation und auch für CSV gibt es schon fertige Routinen 13.1. csv ? CSV File Reading and Writing — Python v2.7.2 documentation Zitieren
Shabutaro Geschrieben 22. Juni 2011 Autor Geschrieben 22. Juni 2011 (bearbeitet) Danke für eure Hilfe. Solange ich nur Zahlen in der Datei habe ist alles kein Problem gerade. Bin jetzt gerade am Suchen wie man nur bestimmte Zeilen/Spalten rauslesen kann, jede Zahl in ein array packt, sodass man auf jede Zahl einzeln Zugriff hat und noch wie man die Zahlen die dann in einer list oder array sind noch teilen kann, da die angaben in Bytes sind und ich die in KB oder MB brauche Wenn da noch einer eben ein Tip für mich hat wäre ich nocheinmal sehr dankbar. //edit: Bevor ich es vergesse: Es handelt sich um .dstat bzw. .data Datein. Und ja, mir steht nur Python zur Verfügung. Shabutaro Bearbeitet 22. Juni 2011 von Shabutaro Zitieren
flashpixx Geschrieben 22. Juni 2011 Geschrieben 22. Juni 2011 5. Data Structures — Python v2.7.2 documentation Zitieren
sylenz Geschrieben 22. Juni 2011 Geschrieben 22. Juni 2011 Moin, wie flashpixx schon sagte sind dafür listen oder dictionarys möglich -> arrays im sinne von php gibt es nicht. Hier mal ein kleiner Codebrocken der alle Logfiles eines Verzeichnisses ausliest, durchgeht und ein Dictionary mit dem Key - Wertepaar von Position 1 und 2 der aktuellen Zeile erzeugt (exemplarisch). Das Dictionary kannst du dann weiterbearbeiten und z.B. mittels matplotlib direkt Graphen erzeugen lassen. logDir = "c:\\dein\\logfile\\pfad" for root,dirs,file in os.walk(logDir): logFile = logDir + str(file[0]) #dateiname ist listenelement an position 0 openFile = open(logFile, "r") tempDict = {} for line in openFile: line = line.strip() #entfernen des Zeilenumbruchs word = line.split(",") #Aufteilen der Zeile anhand definiertem Seperator -> python erzeugt eine Ergebnisliste if not word[0] == '1"time': #workaround damit die erste Zeile nicht angezeigt wird tempDict[word[0]] = word[1] print tempDict [/PHP] Zitieren
flashpixx Geschrieben 22. Juni 2011 Geschrieben 22. Juni 2011 Wenn es eh CSV Daten sind, dann muss ich nicht manuell zeilenweise die Dateien verarbeiten, sondern kann, wie in meinem vorherigen Post über einen CSV-Reader die Daten direkt passend lesen Zitieren
sylenz Geschrieben 22. Juni 2011 Geschrieben 22. Juni 2011 Stimmt, ich habe auch nicht behauptet dass das die einzige Lösung und / oder die einfachste ist ;-). Das CSV-Reader Modul ist sehr handlich, macht aber vermutlich auch nichts anderes als zeilenweise die Datei auszulesen und in eine Liste zu packen Zitieren
Shabutaro Geschrieben 23. Juni 2011 Autor Geschrieben 23. Juni 2011 Ok danke, kann die Daten jetzt alle einlesen. Jetzt habe ich aber trotzdem noch eine Frage Und zwar wie mache ich Folgende abfrage: Wenn die anzahl der eingelesen Daten nicht GENAU 19 ist, überspringe die Zeile und gib eine Fehlermeldung. (der soll dann halt einfach mit der nächsten Zeile weitermachen, aber eine Fehlermeldung im Terminal hinterlassen). Wenn sie genau 19 ist mache ..... (das habe ich schon, also schreibe die werte in das array rein. Also hauptsächlich gehts mir darum, das der automatisch die nächste Zeile bearbeitet, wenn diese nicht genau 19 Werte hat.. weil bis jetzt macht der bei nicht genau 19 werten nur raise Exception("Did not recieve all needed values!") und liest die Datei nicht weiter ein.. was ziemlich nervig bei meiner Testdatei mit 1300 Zeilen ist^^ Irgendwie glaube ich habe stelle ich hier dumme Fragen.. naja.. habe python das erste mal vor 4 Tagen angerührt^^ Zitieren
flashpixx Geschrieben 23. Juni 2011 Geschrieben 23. Juni 2011 Eine Liste hat die Methode "count", bitte lies Dir einmal die Dokumentation durch Zitieren
Shabutaro Geschrieben 23. Juni 2011 Autor Geschrieben 23. Juni 2011 list.count(x) Return the number of times x appears in the list. Und was hilft mir ne Zählfunktion für eine bestimmte variable wenn ich jede Zeile überspringen will die nicht genau 19 Werte aufweisst? Also "Dstat 0.7.0 CSV output" und ähnliches übersrpingen und bei 20-06 03:36:07,1.440,0.655,96.805,0.893,0.026,0.181,2198305.083,3424606.408,0.0,0.0,0.0,0.0,1925.683,5869.014,601661440.0,11915264.0,1919737856.0,5834784768.0 wieder anfangen die Daten einzulesen. Zitieren
flashpixx Geschrieben 23. Juni 2011 Geschrieben 23. Juni 2011 Die Funktion heißt "len( [] )" Zitieren
Shabutaro Geschrieben 23. Juni 2011 Autor Geschrieben 23. Juni 2011 Die Funktion ist mir bekannt, doch wie kann ich damit die Länge von nur 1 Zeile herausbekommen? MIr is nämlich außer readline nichts bekannt was nur auf 1 Zeile zugreifft. Zitieren
flashpixx Geschrieben 23. Juni 2011 Geschrieben 23. Juni 2011 Schau Dir die Funktion des CSV Readers an und was er liefert mit Hilfe von len kann man dann sehr leicht ermitteln, wie viele Spalten in der Zeile vorhanden sind. Zitieren
Shabutaro Geschrieben 24. Juni 2011 Autor Geschrieben 24. Juni 2011 Hab das nun alles ohne den CSV Reader geschafft.. war für mich leichter, da ich den mal garnicht verstehe Naja nun habe ich endlich meine 2 Klassen fertig und kann die kompletten Logs einlesen und für jede reihe einzen die Daten plotten Danke nochmal. Ich geh jetzt ein paar Schönheitsoperationen machen wie z.b. mehr als 1 Linie plotten (sondern alle 4 CPU Daten) etc. cheers&goodbye Shabu Zitieren
Shabutaro Geschrieben 27. Juni 2011 Autor Geschrieben 27. Juni 2011 Sorry das ich euch noch einmal stören muss, aber eine Frage habe ich nun doch noch Wie krieg ich es hinn, dass wenn ich den Graph plotte, der auch bei (0/0) anfängt und nicht nur da wo der niedrigste und der höchste Wert ist. So sieht meine Ausgabe aus.. möchte halt nur das man den kompletten Graphen sieht, nicht nur von da, wo der niedrigste Wert anfängt. Danke schon einmal noch einmal für eure Hilfe Shabu Zitieren
flashpixx Geschrieben 27. Juni 2011 Geschrieben 27. Juni 2011 Das ist eine Einstellung in dem Framework, das Du für die Erzeugung verwendet. Du nennst dieses Framework nicht Zitieren
Shabutaro Geschrieben 28. Juni 2011 Autor Geschrieben 28. Juni 2011 Jops sorry, wollte nicht nen triple post hinlegen Das ist der Code für den kompletten plott: def makeLineChart(self, name): yvalues = self.getData(name) xvalues = self.getData("TIME") width = 0.3 maxx = yvalues[0] i = 1 while i < len(yvalues): if yvalues[i] > maxx: maxx = yvalues[i] i = i + 1 ave=sum(yvalues) / len(yvalues) endtime=datetime.fromtimestamp(xvalues[-1]).strftime("%H:%M:%S") starttime=datetime.fromtimestamp(xvalues[0]) start=str(starttime) end=str(endtime) meanYValues=self.calcMeanArray(yvalues) testticks=range(len(meanYValues)) filepath = raw_input("Where to save the .esp files? ") if maxx != 0: plot(testticks, meanYValues, 'k-') xticks(testticks) yticks(arange(0, maxx, round(maxx/25, 2))) title('dstat plotter: ' + name, size=22) grid(True) maxstr=str(round(maxx, 2)) aver=str(round(ave, 2)) axhline(y=maxx, color='r', label=maxstr) axhline(y=ave, color='g', label=aver) legend(('PlotLine', 'Max Value = '+ maxstr, 'Average Value = ' +aver), loc='best', shadow=True) savefig(filepath + start + " - " +end + " " + name, format="eps") if name != 'ALL': show() else: print name + ": every value is 0, will not be plotted!" close() Hoffe du meinst dies und das hilft dabei Zitieren
flashpixx Geschrieben 28. Juni 2011 Geschrieben 28. Juni 2011 Wäre es evtl zu viel verlangt, dass Du das Framework nennst, mit dem Du arbeitest? Ich kann in Python verschiedene Libraries wie z.B. Gnuplot, Matplot, R... verwenden, um Graphen zu erzeugen. Jede Library wird anders verwendet und hat nun mal einen unterschiedlichen Syntax. Ich empfehle, dass Du einmal die Dokumentation zu Deinem Framework vollständig liest, denn im Normalfall findet man dort die gewünschten Informationen. Geh nicht davon aus, dass jeder hier alle Frameworks kennt und vor allem im Detail weiß, wie welche Klassen / Strukturen verwendet werden. Zitieren
Shabutaro Geschrieben 29. Juni 2011 Autor Geschrieben 29. Juni 2011 Ich kopiere einfach mal meinen ganzen Code.. Was anderes als das habe ich nicht benutzt: import DstatValue from time import * from datetime import * from pylab import * class Plot(object): data = [] xResolution=15 def __init__(self, dstatTextfile): for line in open(dstatTextfile, 'r'): try: self.data.append(DstatValue.Value(line)) except: pass def getData(self, name): fieldValues = [] for value in self.data: fieldValues.append(value.getDataFromField(name)) return fieldValues def calcMeanArray(self, values): to=i=0 ret=[] while(1): total=0 to=i+self.xResolution if to > len(values): to=len(values) for i in range(i, to): total+=values[i] if to == len(values): break mean=total/self.xResolution ret.append(mean) return ret def makeLineChart(self, name): yvalues = self.getData(name) xvalues = self.getData("TIME") width = 0.3 maxx = yvalues[0] i = 1 while i < len(yvalues): if yvalues[i] > maxx: maxx = yvalues[i] i = i + 1 ave=sum(yvalues) / len(yvalues) endtime=datetime.fromtimestamp(xvalues[-1]).strftime("%H:%M:%S") starttime=datetime.fromtimestamp(xvalues[0]) start=str(starttime) end=str(endtime) meanYValues=self.calcMeanArray(yvalues) testticks=range(len(meanYValues)) filepath = raw_input("Where to save the .esp files? ") if maxx != 0: plot(testticks, meanYValues, 'k-') xticks(testticks) yticks(arange(0, maxx, round(maxx/25, 2))) title('dstat plotter: ' + name, size=22) grid(True) maxstr=str(round(maxx, 2)) aver=str(round(ave, 2)) axhline(y=maxx, color='r', label=maxstr) axhline(y=ave, color='g', label=aver) legend(('PlotLine', 'Max Value = '+ maxstr, 'Average Value = ' +aver), loc='best', shadow=True) savefig(filepath + start + " - " +end + " " + name, format="eps") if name != 'ALL': show() else: print name + ": every value is 0, will not be plotted!" close() Zitieren
flashpixx Geschrieben 29. Juni 2011 Geschrieben 29. Juni 2011 Bitte Dokumentation lesen matplotlib: python plotting — Matplotlib v1.0.1 documentation Zitieren
sylenz Geschrieben 29. Juni 2011 Geschrieben 29. Juni 2011 Ich kann Dir gerade nicht ganz folgen: Was genau willst du anzeigen bzw. nicht anzeigen? Matplotlib gibt genau die Werte aus die du ihm übergibst. Mit ylim() kannst du z.B. den maximalen / minimalen Anzeigebereich definieren - oder du filterst die Liste mit den Werten bevor du sie plot() übergibst (um z.B. den Anfangsnullwert zu eliminieren) ... Zitieren
Empfohlene Beiträge
Dein Kommentar
Du kannst jetzt schreiben und Dich später registrieren. Wenn Du ein Konto hast, melde Dich jetzt an, um unter Deinem Benutzernamen zu schreiben.