Рядок Python друкується як [u'String ']


142

Це, безумовно, буде легким, але це насправді клопоче мене.

У мене є сценарій, який читається на веб-сторінці і використовує Beautiful Soup для його розбору. З супу я витягую всі посилання, оскільки остаточна мета - роздрукувати link.contents.

Весь текст, який я розбираю, - це ASCII. Я знаю, що Python розглядає рядки як unicode, і я впевнений, що це дуже зручно, просто не маючи користі для мого сценарію wee.

Кожен раз, коли я йду роздруковувати змінну, яка містить "String", я [u'String']надрукуюсь на екран. Чи є простий спосіб повернути це в просто ascii або я повинен написати регулярний вираз, щоб зняти його?


можливо дублікат набагато більш чітко сформульоване питання (і відповідь): stackoverflow.com/q/2464959/1390788
Terrabits

Чи відповідає це на ваше запитання? Який префікс u в рядку Python?
Терабіти

Відповіді:


118

[u'ABC']буде одноелементним рядком рядків Unicode. Прекрасний суп завжди виробляє Unicode . Отже, вам потрібно перетворити список в одну рядок Unicode, а потім перетворити його в ASCII.

Я точно не знаю, як ви отримали одноелементні списки; учасником вмісту буде список рядків і тегів, що, мабуть, не те, що у вас є. Якщо припустити, що ви дійсно завжди отримуєте список з одним елементом, і що ваш тест справді лише ASCII, ви використовуєте це:

 soup[0].encode("ascii")

Однак переконайтесь, що ваші дані справді ASCII. Це досить рідко. Набагато ймовірніше, що це латинь-1 або utf-8.

 soup[0].encode("latin-1")


 soup[0].encode("utf-8")

Або ви запитаєте Beautiful Soup, яким було оригінальне кодування, і поверніть його в цьому кодуванні:

 soup[0].encode(soup.originalEncoding)

6
Насправді не потрібно робити кодування, оскільки ОП бачить лише рядковий репр, тому що ви бачите що-небудь під час друку списку. Супу [0] буде достатньо, щоб замість repr було показано str, показуючи вміст рядка, а не модифікатор цитати та unicode.
ironfroggy

2
У більшості випадків ви не повинні кодувати текст, представлений як Unicode, до байтів: слід надрукувати Unicode безпосередньо на Python:print(', '.join([u'ABC' , u'...']))
jfs

26

Напевно, у вас є список, що містить один рядок unicode. Це reprє [u'String'].

Ви можете перетворити це до списку байтових рядків, використовуючи будь-які варіанти з наступного:

# Functional style.
print map(lambda x: x.encode('ascii'), my_list)

# List comprehension.
print [x.encode('ascii') for x in my_list]

# Interesting if my_list may be a tuple or a string.
print type(my_list)(x.encode('ascii') for x in my_list)

# What do I care about the brackets anyway?
print ', '.join(repr(x.encode('ascii')) for x in my_list)

# That's actually not a good way of doing it.
print ' '.join(repr(x).lstrip('u')[1:-1] for x in my_list)

1
Будь ласка, уникайте таких жахів, як repr(x).lstrip('u')[1:-1]. Використовуйте щось на зразок: print ", ".join(my_list)замість цього відформатуйте список рядків Unicode.
jfs

1
У коментарі сказано: "Це насправді не дуже хороший спосіб зробити це". Це просто для lolz!
ddaa

9
import json, ast
r = {u'name': u'A', u'primary_key': 1}
ast.literal_eval(json.dumps(r)) 

буде надруковано

{'name': 'A', 'primary_key': 1}

1
цей метод мені виглядає досить мило, чому немає голосів? будь-який вплив на роботу, про який ми повинні турбуватися?
jrich523

8

Якщо ви маєте доступ до / друкує списки окремих елементів (наприклад, послідовно або відфільтровано):

my_list = [u'String'] # sample element
my_list = [str(my_list[0])]

1
ви робите розуміння списку:my_list = [str(my_list[x]) for x in range(len(my_list))]
gevang

4

передайте висновок функції str (), і це видалить перетворений вихід Unicode. також надрукувавши вихід, він видалить з нього теги u ''.


4

[u'String'] являє собою текстове подання списку, що містить рядок Unicode на Python 2.

Якщо ви запускаєте, print(some_list)то це рівнозначно,
print'[%s]' % ', '.join(map(repr, some_list))тобто для створення текстового подання об’єкта Python з типом list, repr()для кожного елемента викликається функція.

Не плутайте об'єкт Python і його текстове представлення - repr('a') != 'a'і навіть текстове представлення тексту подання різний: repr(repr('a')) != repr('a').

repr(obj)повертає рядок, що містить представлений об'єкт для друку. Її мета - бути однозначним поданням об’єкта, який може бути корисним для налагодження, в системі REPL. Часто eval(repr(obj)) == obj.

Щоб уникнути виклику repr(), ви можете надрукувати елементи списку безпосередньо (якщо вони є всіма рядками Unicode), наприклад: print ",".join(some_list)—друкує список розділених комами рядків:String

Не кодуйте рядок Unicode до байтів, використовуючи жорстке кодування символів, друкуйте Unicode безпосередньо замість цього. В іншому випадку код може вийти з ладу, оскільки кодування не може представляти всіх символів, наприклад, якщо ви намагаєтеся використовувати 'ascii'кодування з символами, які не є ascii. Або код мовчки виробляє mojibake (пошкоджені дані передаються далі в конвеєр), якщо середовище використовує кодування, несумісне з жорстко кодованим кодуванням.


3

Використовуйте dirабо typeна 'рядок', щоб дізнатися, що це таке. Я підозрюю, що це один з тегів об’єктів BeautifulSoup, який друкує як рядок, але насправді це не один. В іншому випадку це всередині списку, і вам потрібно перетворити кожен рядок окремо.

У будь-якому випадку, чому ви заперечуєте проти використання Unicode? Якась конкретна причина?


Я дивився на BeautifulSoup з останніх кількох днів. Я не міг зрозуміти, як gnuchu отримає u ['string'] not [u'String ']. Його коментар до Ендрю Яффе, здається, підтверджує, що це список.
батбрат

3

Ти справді маєш на увазі u'String'?

У будь-якому випадку, ви не можете просто зробити, str(string)щоб отримати рядок, а не unicode-рядок? (Це має бути різним для Python 3, для якого всі рядки є unicode.)


Я повинен був бути зрозумілішим. Я використовую str (), але все ж отримую вихід, як показано нижче, коли друкую. [u'ABC '] [u'DEF'] [u'GHI '] [u'JKL'] Дані знімають як текст із веб-сторінки, потім вставляють у базу даних (Google Appstore), потім отримують та друкують.
гнучу


-1

Можливо, я не розумію, чому я не можу просто отримати element.text, а потім перетворити його, перш ніж використовувати його? наприклад (не знаю, чому ви це зробите, але ...) знайдіть усі елементи міток веб-сторінки та повторіть між ними, поки не знайдете те, що називається MyText

        avail = []
        avail = driver.find_elements_by_class_name("label");
        for i in avail:
                if  i.text == "MyText":

Перетворіть рядок з i і зробіть все, що ви хотіли зробити ... можливо, їм щось не вистачає в оригінальному повідомленні? або це було те, що ви шукали?


Ви пропускаєте частину, де йдеться про те, як зробити "Перетворити рядок з i".
Натан Туггі

Аааа, дякую за всі коментарі, я думав, що проблема отримує значення для конвертації
Стівен

але щоб бути справедливим i.text - це фактичне значення рядка, не потрібно "витягувати його з масиву", як деякі люди пропонують, якщо для елементу етикетки, наприклад, є текстове значення [u'String '] i.text буде Струнна
Стівен
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.