Plots erstellen und bearbeiten (netCDF-Files)

mit matplotlib, NumPy, pandas, SciPy, SymPy und weiteren mathematischen Programmbibliotheken.
Antworten
Benutzeravatar
Ronsen90
User
Beiträge: 19
Registriert: Montag 22. Juni 2015, 10:46
Wohnort: Leipzig und Neustrelitz

Hallo liebe Python-Gemeinde,

ich bin ein totaler Anfänger beim Programmieren, muss aber jetzt auf Arbeit mit Python (Version 2.7) Plots von Daten in netCDF-Dateien erstellen. Ich habe auch schon ein paar grobe Ergebnisse zusammenbekommen, aber ich tu mich sehr schwer mit dem Feinschliff.
Hier mal ein Beispielprogramm:

from netCDF4 import Dataset
from matplotlib import pyplot
obj = Dataset("Ronny/MCOL2015/MCOL2015_incmp_006/mcol_trop_incmppyrnet_l1_rsds_v00_20150505000000.nc", "r")
for v in obj.variables:
_____print v # die Unterstriche sollen nur die Einrückung demonstrieren
print obj.variables["station_id"][:]
id = obj.variables["station_id"][:]
strahlung = obj.variables["rsds"][:,:]
zeit = obj.variables["time"][:]
pyplot.plot(zeit,strahlung[:,:])
pyplot.ylabel("Strahlungsintensitaet")
pyplot.xlabel("Zeit")
pyplot.show()

Meine Ausgabe sieht so aus:
runfile('/home/badeke/Bearbeitung von netCDF.py', wdir='/home/badeke')
station_id
lon
lat
zag
time
time_bnds
rsds
rsds_flag
[ 1 4 5 6 8 15 16 19 21 22 26 30 34 35 37 40 42 43 46 49 50 51 53 54 55
57 62 63 64 68 71 72 74 75 77 78 80 81 84 87 88 89 90 91 92 94 95 96 98 99]

http://www.bilder-upload.eu/show.php?fi ... 968542.jpg

Wie ihr seht, werden in meinem Bild die Messungen aller Station-IDs dargestellt (sehr viele Graphen übereinander). ich würde gerne nur die Graphen für bestimmte Station-IDs darstellen. Kann mir jemand sagen, was ich dafür machen muss?
Außerdem kann man im Bild auf der x-Achse sehen, dass die Zeit nicht sonderlich gut dargestellt wird. Ich würde gerne die Achse noch umrechnen, aber dafür müsste ich erst mal die Zeitpunkte einlesen und irgendwie eine Umrechnungsformel eingeben. Kann mir damit jemand helfen.
Benutzeravatar
Kebap
User
Beiträge: 687
Registriert: Dienstag 15. November 2011, 14:20
Wohnort: Dortmund

Hallo Ronsen90, willkommen bei Python und im Forum!
Ronsen90 hat geschrieben: _____print v # die Unterstriche sollen nur die Einrückung demonstrieren
Wenn du beim Schreiben deines Beitrags auf den "Code" Knopf drückst, und deinen Code dann innerhalb des Blocks einfügst, wird die Einrückung normal angezeigt. :mrgreen:
MorgenGrauen: 1 Welt, 8 Rassen, 13 Gilden, >250 Abenteuer, >5000 Waffen & Rüstungen,
>7000 NPC, >16000 Räume, >200 freiwillige Programmierer, nur Text, viel Spaß, seit 1992.
Benutzeravatar
Ronsen90
User
Beiträge: 19
Registriert: Montag 22. Juni 2015, 10:46
Wohnort: Leipzig und Neustrelitz

Oh, gut zu wissen, gleich mal ausprobieren...

Code: Alles auswählen

from netCDF4 import Dataset
from matplotlib import pyplot
obj = Dataset("Ronny/MCOL2015/MCOL2015_incmp_006/mcol_trop_incmppyrnet_l1_rsds_v00_20150505000000.nc", "r")
for v in obj.variables:
    print v
print obj.variables["station_id"][:]
id = obj.variables["station_id"][:]
strahlung = obj.variables["rsds"][:,0] # geändert
zeit = obj.variables["time"][:]
pyplot.plot(zeit,strahlung) # geändert
pyplot.ylabel("Strahlungsintensitaet")
pyplot.xlabel("Zeit")
pyplot.show()
Ich habe auch schon etwas Hilfe bekommen. Jetzt zeigt das Programm schon mal nur den Plot zur ersten ID an.
Benutzeravatar
MagBen
User
Beiträge: 799
Registriert: Freitag 6. Juni 2014, 05:56
Wohnort: Bremen
Kontaktdaten:

Probier das mal:

Code: Alles auswählen

from netCDF4 import Dataset
from matplotlib import pyplot
obj = Dataset("Ronny/MCOL2015/MCOL2015_incmp_006/mcol_trop_incmppyrnet_l1_rsds_v00_20150505000000.nc", "r")
id = obj.variables["station_id"][:]
zeit = obj.variables["time"][:]
strahlung = obj.variables["rsds"][:]
for i in range(strahlung.shape[1]):
    pyplot.figure()
    pyplot.title("Spalte %i" % (i+1))
    pyplot.plot(zeit,strahlung[:,i])
    pyplot.ylabel("Strahlungsintensitaet")
    pyplot.xlabel("Zeit")
pyplot.show()
a fool with a tool is still a fool, www.magben.de, YouTube
Benutzeravatar
Ronsen90
User
Beiträge: 19
Registriert: Montag 22. Juni 2015, 10:46
Wohnort: Leipzig und Neustrelitz

Hallo MagBen,

Ich hab dein Programm ausprobiert und es gibt alle Plots aus, das ist für den Anfang schon ziemlich gut. Danke dafür! Inzwischen hat sich mein Chef der Sache angenommen, auch was die Zeitanpassung der x-Achse betrifft. Jetzt hab ich ein Programm, bei dem ich selbst das Verzeichnis herein kopieren kann und die Stations-ID und ausgegeben wird eben nur dieses eine Diagramm für die bestimmte Station.

Code: Alles auswählen

from netCDF4 import Dataset
from matplotlib import pyplot
import datetime, pytz
from matplotlib import dates


dateiname = raw_input("Bitte das Verzeichnis eingeben: ") # z.B. Ronny/MCOL2015/MCOL2015_incmp_006/mcol_trop_incmppyrnet_l1_rsds_v00_20150506000000.nc
obj = Dataset(dateiname, "r")
for v in obj.variables:
    print v
print "Liste der Stationsnummern:"
print obj.variables["station_id"][:]
print "Angepasste Liste:"
print "[ 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24"
print " 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49]"
id = obj.variables["station_id"][:]
k = raw_input("Bitte die zu untersuchende Stationsnummer aus der angepassten Liste eingeben: ")
k = int(k)
strahlung = obj.variables["rsds"][:,k]
zeit = obj.variables["time"][:]
dt_base=datetime.datetime(1970,1,1,0,0,0).replace(tzinfo=pytz.UTC)
zeit = [ dt_base+datetime.timedelta(seconds=zeit[i]) for i in range(len(zeit))]
zeit = dates.date2num(zeit)
fmt = dates.DateFormatter('%H:%M')

fig = pyplot.figure()
ax = fig.add_subplot(111)

ax.xaxis.set_major_locator(dates.HourLocator())
ax.xaxis.set_major_formatter(fmt)


ax.plot(zeit,strahlung)
pyplot.ylabel("Strahlungsintensitaet")
pyplot.xlabel("Zeit")
pyplot.xticks(rotation ='vertical')

pyplot.show()
Die Ausgabe umfasst unter anderem folgendes:
Liste der Stationsnummern:
[ 1 4 5 6 8 15 16 19 21 22 26 30 34 35 37 40 42 43 46 49 50 51 53 54 55
57 62 63 64 68 71 72 74 75 77 78 80 81 84 87 88 89 90 91 92 94 95 96 98 99]
Angepasste Liste:
[ 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49]

Darunter folgt die Eingabe einer Nummer aus der Angepassten Liste und die Ausgabe eines Plots.

Mein neues Problem ist jetzt, dass ich gerne direkt die Stationsnummer eingeben würde, anhand derer mir das Programm den richtigen Plot ausgibt. Aktuell muss ich quasi die angepasste Liste nehmen, weil 0 für Nummer 1, 1 für Nummer 4 usw. steht. Ich müsste also irgendwie einen Verweis einfügen, der die Listen verknüpft. Falls jemand eine Idee dafür hätte, wäre ich sehr dankbar. :)
Sirius3
User
Beiträge: 17754
Registriert: Sonntag 21. Oktober 2012, 17:20

@Ronsen90: Zeile 22 ist ein Antipattern, in Python iteriert man direkt über das Array, statt über den Index:

Code: Alles auswählen

zeit = [dt_base + datetime.timedelta(seconds=z) for z in zeit]
und warum so kompliziert? Zeile 20 bis 23 ergibt einfach:

Code: Alles auswählen

zeit = 800000 + obj.variables["time"] / (24.0 * 3600.0)
Das Problem mit der Stationsnummer läßt sich einfach über Listen und Index lösen:

Code: Alles auswählen

stations_nummer = int(raw_input("Bitte die zu untersuchende Stationsnummer aus der angepassten Liste eingeben: "))
stations_index = list(obj.variables["station_id"]).index(stations_nummer)
Benutzeravatar
Ronsen90
User
Beiträge: 19
Registriert: Montag 22. Juni 2015, 10:46
Wohnort: Leipzig und Neustrelitz

Hi Sirius3!

Die Zeilen für die Zeit habe ich jetzt mal so gelassen. Ich habe zwar versucht, sie zu vereinfachen, aber das ergab einen Error... ist ja nicht so schlimm, der Teilabschnitt macht ja, was er machen soll.

Nach ein bisschen Herumprobieren habe ich das Problem mit der Stationsnummer dank deiner Hilfe lösen können. Vielen Dank!
Antworten