Seite 1 von 1

[Hilfe] YoutubeAPI || If Statement Fehler

Verfasst: Freitag 7. Februar 2020, 15:17
von Lotus
Hey,
ich habe heute angefangen mit dem YoutubeAPI zu programmieren und ich wollte ein Programm schreiben das mir die ID von einem Channel oder Video anzeigt mit custom User input.

Probelm:
Wenn ich ein Video suchen will, denkt das Programm aus irgend einem Grund das ich "channel" oder "Channel" eingegeben habe und Ich weis echt nicht wieso.
Hier ist mein Code:

Code: Alles auswählen

from apiclient.discovery import build
from time import sleep

api_key = "zensiert"
youtube = build("youtube", "v3", developerKey=api_key)


def search_channel(q):
    rq = youtube.search().list(q="GommeHD", part="snippet", type="channel", maxResults=1)
    rs = rq.execute()
    for item in rs["items"]:
        print("ChannelID: " + item["snippet"]["channelId"])

def search_video(q, maxResults):
    rq_2 = youtube.search().list(q="", part="snippet", type="video", maxResults=1)
    rs_2 = rq_2.execute()
    for item in rs_2["items"]:
        print("VideoID: " + item["snippet"]["videoId"])

answer = input("Do you want to find the ID of a [video] or of a [channel]: ")

if answer == "channel" or "Channel":
    sleep(1)
    q = input("Channel you want to search up: ")
    sleep(1)
    print("Searching...")
    sleep(1)
    search_channel(q)
elif answer == "video" or "video":
    sleep(1)
    q = input("Video you want to search up (exact title): ")
    sleep(1)
    maxresults = input("The max. results: ")
    sleep(1)
    print("Searching...")
    search_video(q, maxResults)
    sleep(1)
else:
    print("no existing option called: " + str(answer))
Danke im voraus! -Lotus

Re: [Hilfe] YoutubeAPI || If Statement Fehler

Verfasst: Freitag 7. Februar 2020, 15:26
von __blackjack__
@Lotus: ``or`` ist ein binärer Operator und kein umgangssprachliches ”oder”. Da gibt es einen Wert auf der linken Seite des Operators und einen Wert auf der rechten Seite des Operators und bei ``answer == "channel" or "Channel"`` ist es sogar egal ob ``==`` nun stärker bindet als ``or`` oder nicht, in beiden Varianten macht es keinen Sinn das so zu schreiben. Was da ausgewertet wird ist ``answer == "channel"`` und das Ergebnis davon wird dann logisch ”oder”-veknüpft mit "Channel" und "Channel" ist wahr weil es keine leere Zeichenkette ist, und damit ist dieser Ausdruck *immer* wahr, egal was `answer` für einen Wert hat.

Auf der linken Seite vom ``or`` müsste auch ein Vergleich stehen, oder aber man wandelt `answer` vor dem Vergleich zum Beispiel in Kleinbuchstaben, dann braucht man das nur noch mit "channel" zu vergleichen und es ist egal ob und welche Buchstaben der Benutzer in Grossbuchstaben eintippt.

Re: [Hilfe] YoutubeAPI || If Statement Fehler

Verfasst: Samstag 8. Februar 2020, 14:53
von __blackjack__
@Lotus: Noch ein paar Anmerkungen zum Code:

Auf Modulebene gehört nur Code der Konstanten, Funktionen, und Klassen definiert. Das Hauptprogramm steht üblicherweise in einer Funktion die `main()` heisst.

Daraus folgt direkt das Funktionen (und Methoden) alles was sie ausser Konstanten als Argument(e) übergeben bekommen.

Konstanten werden KOMPLETT_GROSS geschrieben, um sie als solche erkennen zu können. Ausser Klassen (MixedCase) schreibt man sonstige Namen klein_mit_unterstrichen.

Die `sleep()`-Aufrufe machen keinen Sinn sondern nerven den Benutzer nur mit unnötiger Wartezeit.

Keine kryptischen Abkürzungen als Namen. Namen sollen dem Leser die Bedeutung von Werten vermitteln und nicht zum Rätselraten zwingen. Man nummeriert auch keine Namen. Ich verstehe auch gar nicht warum da eine `_2` dran hängt, das macht keinen Sinn.

Beide `search_*()`-Funktionen bekommen Argument die sie alle überhaupt nicht verwenden.

Letztlich sehen beide Suchfunktionen fast gleich aus:

Code: Alles auswählen

def search_channel(youtube, query, max_results):
    result = (
        youtube.search()
        .list(q=query, part="snippet", type="channel", maxResults=max_results)
        .execute()
    )
    for item in result["items"]:
        print("ChannelID: " + item["snippet"]["channelId"])


def search_video(youtube, query, max_results):
    result = (
        youtube.search()
        .list(q=query, part="snippet", type="video", maxResults=max_results)
        .execute()
    )
    for item in result["items"]:
        print("VideoID: " + item["snippet"]["videoId"])
Das heisst das ist eigentlich *eine* Funktion die sich nur durch die Zeichenkette "channel" oder "video" unterscheided.

Dann sind die beiden letzten Zeilen in ``if``/``elif`` im Hauptprogramm fast gleich und man sollte die hinter das Konstrukt ziehen, um Codewiederholung im Quelltext zu vermeiden.

Zwischenstand (ungetestet):

Code: Alles auswählen

#!/usr/bin/env python3
from apiclient.discovery import build

API_KEY = "zensiert"


def search(youtube, query, type_, max_results):
    result = (
        youtube.search()
        .list(q=query, part="snippet", type=type_, maxResults=max_results)
        .execute()
    )
    id_name = type_ + "Id"
    for item in result["items"]:
        print(f"{id_name.title()}:", item["snippet"][id_name])


def main():
    youtube = build("youtube", "v3", developerKey=API_KEY)
    type_ = (
        input("Do you want to find the ID of a [video] or of a [channel]: ")
        .strip()
        .lower()
    )
    if type_ == "channel":
        query = input("Channel you want to search: ")
        max_results = 1
    elif type_ == "video":
        query = input("Video you want to search (exact title): ")
        max_results = int(input("Max. number of results: "))
    else:
        print(f"no existing type called: {type_}")
        return

    print("Searching...")
    search(youtube, query, type_, max_results)


if __name__ == "__main__":
    main()