Archive for the ‘Python / SciPy / pandas’ Category.

Mit Python suchen und ersetzen in CSV-Dateien (mit pandas)

Nachdem wir uns im letzten Artikel angeschaut hatten, wie man mit openpyxl Funktionen Felder in CSV-Dateien mit Werten aus Excel-Dateien ersetzen kann, heute nun die pandas Implementierung dessen.

Sie nutzt auch openpyxl zum Einlesen der Excel-Datei, da xlrd, das bisher von pandas genutzte Modul für Excel-Dateien, den Support für XLSX Formate eingestellt hat.

Die Arbeitsweise des Codes ist recht einfach. pandas liest die Datei, da die Tabelle nicht links oben anfängt, werden die erste Zeile und Spalte ignoriert und die Spalten passend benannt. Dann iterieren wird durch den Dataframe und ersetzen munter…

import pandas as pd
 
path = "python_test.xlsx"
df = pd.read_excel(path,engine='openpyxl',
                   sheet_name='Tabelle2',skiprows=1,
                   usecols={1,2},header=None)
 
df = df.rename(columns={1: "Key", 2: "Value"})
 
with open('Python_test.txt') as input_file:
    text = input_file.read()
 
    for index, row in df.iterrows():
        text = text.replace(row['Key'] ,str(row['Value']))
 
    with open('Python_test_output_pd.txt','w') as output_file:
        output_file.write(text)

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Mit Python suchen und ersetzen in CSV Dateien

Nachdem wir bereits mit Excel und VBA Platzhalter in CSV Dateien gesucht und mit Inhalten ersetzt haben heute das ganze mit Python und OpenPyxl.

Ausgangspunkt ist eine Exceldatei „python_test.xlsx“ mit einer Named Range „Felder“ im Tabellenblatt „Tabelle2“.

Mit der openpyxl Bibliothek laden wir das Excel-Blatt und holen uns die Inhalte der Range in ein Dictionary. Jeden der Keys aus dem Dictionary suchen wir dann in der CSV Datei und ersetzen ihn gegen den Wert aus der Excel-Datei.

# -*- coding: utf-8 -*-
import openpyxl 
 
path = "python_test.xlsx"
workbook = openpyxl.load_workbook(path) 
 
def get_sheet_and_location(workbook, named_range):
    x = list(workbook.defined_names['Felder'].destinations)[0]
    return x[0], x[1].replace('$','').split(':')[0],x[1].replace('$','').split(':')[1]
 
 
sheet, start, stop = get_sheet_and_location(workbook,'Felder')
worksheet = workbook[sheet]
rng=worksheet[start:stop] 
 
replacements = {}
 
for row in rng:
    c1, c2 = row
    replacements[c1.value] = c2.value
 
 
 
with open('Python_test.txt') as input_file:
 
    text = input_file.read()
 
    for key in replacements:
        text = text.replace(key,str(replacements[key]))
 
    with open('Python_test_output.txt','w') as output_file:
        output_file.write(text)

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Mailman Spammer mit Python blocken – Teil 2

Ausgehend von meinem ersten Artikel zu diesem Thema habe ich jetzt noch eine Erweiterung des Skripts vorgenommen. Als Spammer erkannte E-Mail-Adressen werden jetzt auch automatisch geblockt.

Dazu suche ich alle „Dauerhaft von der Liste verbannen“ Checkboxen — ihre Namen beginnen alle mit „ban-“ — und klicke sie.

from selenium.webdriver import Firefox
from selenium.webdriver.firefox.options import Options
from selenium.common.exceptions import NoSuchElementException
 
opts = Options()
browser = Firefox(executable_path=r"C:\geckodriver-v0.27.0\geckodriver.exe",
                  options=opts)
browser.implicitly_wait(3)
 
browser.get('<url>')
search_form = browser.find_element_by_name('adminpw')
search_form.send_keys('<password>')
search_form.submit()
 
try:
    field = browser.find_element_by_name('discardalldefersp')
    field.click()
    browser.implicitly_wait(3)
    submit = browser.find_element_by_name('submit')
    submit.click()
except NoSuchElementException:
    print('No new messages to be discarded')
 
browser.implicitly_wait(3)
 
fields = browser.find_elements_by_xpath("//input[@value='3']")
emails = browser.find_elements_by_xpath('//td[contains(text(),"@")]')
banfields = browser.find_elements_by_xpath('//input[contains(@name,"ban-")]')
 
if len(fields) == 0:
    print('No new requests to be discarded, closing browser')
    browser.close()
else:
    if len(fields) == len(emails) and len(fields) == len(banfields) :
        zipped_list = list(zip(emails, fields, banfields))
 
        for i in zipped_list:
            email, field, banfield = i
            if not email.text.endswith(')'):
                field.click()
                banfield.click()

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Siemens Nixdorf VFD Displays ansteuern mit Python

Vor einigen Monaten habe ich mir günstig auf Ebay ein Siemens Nixdorf BA 63 USB Display gekauft, das VFD (vacuum fluorescent display) Technologie für die Anzeige nutzt und 2×20 Zeichen bietet.

Als passendste Python-Bibliothek nutze ich https://github.com/stephanemouton/VFD-WCN, die Anleitung zur Einrichtung wird im github sehr gut beschrieben.

Hier der Quellcode, der die Ausgabe im Bild erzeugt:

from vfdpos import *
factory=WincorNixdorfDisplayFactory()
VFDs = factory.get_vfd_pos()
MyVFD = VFDs[0]

MyVFD.clearscreen()

MyVFD.poscur(1, 1)
MyVFD.write_msg("Hallo")
MyVFD.write_msg("Welt")
MyVFD.write_msg("1234567abcd\r")
MyVFD.poscur(2, 1)
MyVFD.write_msg("ABCDEFüäößi")

MyVFD.close()

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Fortnite teilweise blockieren – Erweiterung um Status

This entry is part 2 of 2 in the series Pi-Hole

Im ersten Artikel zu diesem Thema hatte ich schon beschrieben, wie man mit Pi-Hole DNS Lookups so unterbinden kann, dass man Fortnite oder andere Zeitfresser temporär blockieren kann. In diesem Teil erweitern wir das Skript um eine Statusabfrage. Dazu fügen wir einfach eine Route hinzu, die die URL mit dem Parameter /status abfragt. Dann wird der Inhalt der epicstatus.txt abgefragt, die von den Routen /on und /off mit dem Zeitstempel versehen wurde.

import os
from datetime import datetime
from flask import Flask
 
app = Flask(__name__)
 
@app.route('/')
def index():
    return('<h1>Use /off and /on to enable/disable blocking, /status to get epic.log</h1>')
 
@app.route('/<param>')
def setter(param):
    if param=='status':
        with open('/home/pi/epicstatus.txt') as f:
            content = f.read()
            return '<h2>' + content + '</h2>'
    if param=='off':
        os.system("/usr/local/bin/pihole regex '.*\.epicgames.com' > /home/pi/epic.log")
        now = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
        with open('/home/pi/epicstatus.txt','w') as ausgabe:
            ausgabe.write(now + ' off')
        return '<h1>Turning off Fortnite</h1>'
    elif param=='on':
        os.system("/usr/local/bin/pihole regex -d '.*\.epicgames.com' > /home/pi/epic.log")
        now = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
        with open('/home/pi/epicstatus.txt','w') as ausgabe:
            ausgabe.write(now+ ' on')
        return '<h1>Turning on Fortnite</h1>'

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Dateien kopieren, zippen und löschen mit Python

Hier ein kurzes Beispiel, wie man mit Python-Modulen Dateien kopieren, zippen und löschen kann.

import zipfile
from shutil import copyfile
from os import unlink
 
# copy file
copyfile('dtk-authoryear.bbx'  , './dtk-bibliography/dtk-authoryear.bbx')
copyfile('dtk-authoryear.dbx'  , './dtk-bibliography/dtk-authoryear.dbx')
copyfile('dtk-bibliography.pdf', './dtk-bibliography/dtk-bibliography.pdf')
copyfile('dtk-bibliography.tex', './dtk-bibliography/dtk-bibliography.tex')
 
# create the zip file
with zipfile.ZipFile('dtk-bibliography.zip', 'w', zipfile.ZIP_DEFLATED) as z:
    z.write('./dtk-bibliography/README.md')
    z.write('./dtk-bibliography/dtk-authoryear.bbx')
    z.write('./dtk-bibliography/dtk-authoryear.dbx')
    z.write('./dtk-bibliography/dtk-bibliography.pdf')
    z.write('./dtk-bibliography/dtk-bibliography.tex')
 
# delete copied files
unlink('./dtk-bibliography/dtk-authoryear.bbx')
unlink('./dtk-bibliography/dtk-authoryear.dbx')
unlink('./dtk-bibliography/dtk-bibliography.pdf')
unlink('./dtk-bibliography/dtk-bibliography.tex')

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Mailman Spammer mit Python blocken

Für Dante e.V. betreue ich einige E-Mail-Listen auf mailman-Basis, die seit einigen Tagen von Spammern geflutet werden. Jeden Tag sind dutzende bis hunderte Aufnahme-Requests in der Liste, die ich manuell wegwerfen müsste. Nachdem ich dies einmal händisch getan hatte, musste eine automatische Lösung gefunden werden.

Die Lösung bestand darin, einen Treiber für Firefox („geckodriver“) zu installieren, der das Fernsteuern des Browsers erlaubt. Dann kann mittels selenium Modul die Steuerung aus Python heraus erfolgen. Unten der wesentliche Quellcode als Basis für eigene Arbeiten, den Teil zum Erkennen von legitimen Anfragen habe ich weggelassen.

Nachtrag vom 25.10.2020: Siehe auch die Erweiterung unter https://www.uweziegenhagen.de/?p=4420

# -*- coding: utf-8 -*-
"""
https://www.edureka.co/community/47679/is-it-possible-to-run-headless-browser-using-python-selenium
"""
 
from selenium.webdriver import Firefox
from selenium.webdriver.firefox.options import Options
 
opts = Options()
#opts.set_headless() # Ich will sehen, wie selenium arbeitet
#assert opts.headless  # Operating in headless mode
browser = Firefox(executable_path=r"C:\Users\Uwe\Downloads\geckodriver-v0.27.0-win64\geckodriver.exe", options=opts)
browser.implicitly_wait(3)
 
# einloggen
browser.get('<url des mailman admin panels')
search_form = browser.find_element_by_name('<passwortfeld_ID>')
search_form.send_keys('<adminpasswort>')
search_form.submit()
 
#wegwerfen Button pro Zeile
fields = browser.find_elements_by_xpath("//input[@value='3']")
#email Adresse des Spammers
emails = browser.find_elements_by_xpath('//td[contains(text(),"@")]')
 
if len(fields) == len(emails):
    zipped_list = list(zip(emails, fields))
 
    for i in zipped_list:
        email, field = i
        field.click()

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

„Spiele“-Kritik: While True learn()

Per Zufall bin ich vor einigen Tagen auf ein Juwel im Steam-Shop gestoßen: „while True learn()“. Es ist kein Spiel im klassischen Sinne, sondern mehr eine Simulation zum Lernen von KL/ML-Algorithmen.

Die Geschichte ist schnell erzählt: Programmierer programmiert, kommt nicht weiter, seine Katze übernimmt und erklärt ihm in Katzensprache, was er tun muss. Da er kein Katzisch spricht, baut er mit Hilfe aus dem Netz schrttweise ein System zur Verständigung mit der Mieze.

Das Spiel geht anfangs recht einfach los, ein oder zwei Blöcke positionieren, Verbindungslinien setzen, los.

Über zeitliche Einschränkungen und Kostendruck kommt man aber schnell an den Punkt, an dem man denken muss.

Von mir eine absolute Empfehlung!

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Erste Schritte mit Flask

Hier ein Link zu einem Video, das die ersten Schritte mit Flask zeigt: https://www.youtube.com/watch?v=QjtW-wnXlUY

Über set FLASK_APP=fl-01.py (wenn der Name der Datei so lautet) und flask run startet man das ganze.

from flask import Flask
 
app = Flask(__name__)
 
@app.route('/')
def index():
    return('<h1>Hello World</h1>')
 
 
@app.route('/<name>')
def namer(name):
    return('<h1>Hello {}</h1>').format(name)

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website

Die „passendste“ Datei mit Python ermitteln (fuzzywuzzy)

Für eine Anwendung habe ich eine Möglichkeit gesucht, die „passendste“ Datei in einem Verzeichnis zu suchen. Dies kann relevant sein, wenn die Anwendung eine bestimmte Datei in einem Verzeichnis erwartet, die aber leicht anders benannt wurde als es die Vorgabe erfordert.

Das folgende Beispielprogramm nutzt die Levenshtein-Funktionen der fuzzywuzzy Bibliothek, um die Datei zu finden, die das größte Maß an Gleichheit zum Muster besitzt.

Man kann natürlich auch RegExps benutzen, mit der fuzzywuzzy Bibliothek ist es aber auch recht intuitiv.

# -*- coding: utf-8 -*-
import os
from fuzzywuzzy import fuzz
 
def guess_file(template, path):
    max_ratio = 0
    file_max_ratio = ''
 
    for file in os.listdir(path):
        file_wo_suffix = os.path.splitext(file)[0]
 
        ratio = fuzz.ratio(file_wo_suffix, template)
        if ratio > max_ratio:
            max_ratio = ratio
            file_max_ratio = file
 
    return(file_max_ratio, max_ratio)
 
 
print(guess_file('Meine Inputdaten','R:/'))

Uwe

Uwe Ziegenhagen likes LaTeX and Python, sometimes even combined. Do you like my content and would like to thank me for it? Consider making a small donation to my local fablab, the Dingfabrik Köln. Details on how to donate can be found here Spenden für die Dingfabrik.

More Posts - Website