поведение переменой в функции и with выражении

как коректно создать "глобальную" переменую чтобы можно было нормально работать с with


    def get_all_urls(self):

        urls_list = list()

        with self.connect:
            sql = self.cursor.execute("SELECT url FROM urls;")
            urls_list = sql.fetchall()

        url_replace = lambda x: x[3:len(x)-4]

        return list(map(url_replace, urls_list))


результат программы :

[(), (), (), (), (), (), (), (), (), (), ()]

в итоге в with выражении создается свой список urls_list который не виден всей функции а urls_list "глобальный" не используется и просто возвращается пустым а функция должна возвращать список ссылок , так как же корректно использовать urls_list


Ответы (1 шт):

Автор решения: CrazyElf

Поскольку мои предположения из комментариев оказались верными, оформлю в ответ.

sql.fetchall() видимо возвращает список кортежей вроде такого:

[('http://url1',), ('http://url2',), ('http://url3',), ('http://url4',), ...]

В результате ваш слайс работает с кортежем, а не со строкой. А поскольку в кортеже всего один элемент, то слайс [3:...] возвращает пустой кортеж. Чтобы добраться до строки в первом элементе кортежа можно сделать так:

x[0][3:len(x[0])-4]

Но вообще с URL лучше работать с помощью специальных модулей библиотек, например urllib.parse, там есть методы для корректного разбиения URL на части. Это лучше и стандартнее, чем использовать слайсы.

Насчёт глобальной переменной: лучше вообще не использовать глобальные переменные. Хотите что-то передать в функцию - передавайте через аргументы функции. Хотите получить результат работы функции - передавайте его прозрачно - через return. Если вам нужно вернуть несколько разных объектов из функции - верните их через запятую и "распакуйте" результат вызова функции в несколько переменных, в питоне это очень удобно организовано.

→ Ссылка