Перетворіть список Python із рядками все в малі чи великі регістри


261

У мене є змінна списку python, яка містить рядки. Чи є функція python, яка може перетворити всі рядки за один прохід у малі і навпаки, великі регістри?


Чому «за один прохід»? Чи задумуєтесь ви про можливість прийому декількох пропусків?
— Джон Махін

Яким повинен бути вихід?
— O.rka

Відповіді:


440

Це можна зробити зі списком розумінь. Вони в основному мають форму [function-of-item for item in some-list]. Наприклад, для створення нового списку, де всі елементи мають нижній регістр (або верхній регістр у другому фрагменті), ви використовуєте:

>>> [x.lower() for x in ["A","B","C"]]
['a', 'b', 'c']

>>> [x.upper() for x in ["a","b","c"]]
['A', 'B', 'C']

Ви також можете використовувати mapфункцію:

>>> map(lambda x:x.lower(),["A","B","C"])
['a', 'b', 'c']
>>> map(lambda x:x.upper(),["a","b","c"])
['A', 'B', 'C']

12
Функція карти працює так, як очікувалося в python2, однак у python3 ви загортаєте карту у список, наприклад:list(map(lambda x:x.upper(),["a","b","c"]))
— Tom S

39
Друга пропозиція з картою є правильною, але марною. Немає сенсу робити лямбда-функцію . Просто використовуйтеmap(str.lower, ["A","B","C"])
— фралау

1
Коли я намагаюся надрукувати список після цього дзвінка, нічого не змінюється. Чому так?
— імітує

1
@mimic Трохи запізнився, але для людей, які стикаються з цим, я здогадуюсь, що ваше питання було, ймовірно, тим, що ви не присвоювали результат розуміння списку до свого списку. Просто виконання розуміння списку повертає значення, але не присвоює його змінній списку.
— Майкл Колбер

52

Окрім легкого для читання (для багатьох людей), розуміння списку також виграють швидкісну гонку:

$ python2.6 -m timeit '[x.lower() for x in ["A","B","C"]]'
1000000 loops, best of 3: 1.03 usec per loop
$ python2.6 -m timeit '[x.upper() for x in ["a","b","c"]]'
1000000 loops, best of 3: 1.04 usec per loop

$ python2.6 -m timeit 'map(str.lower,["A","B","C"])'
1000000 loops, best of 3: 1.44 usec per loop
$ python2.6 -m timeit 'map(str.upper,["a","b","c"])'
1000000 loops, best of 3: 1.44 usec per loop

$ python2.6 -m timeit 'map(lambda x:x.lower(),["A","B","C"])'
1000000 loops, best of 3: 1.87 usec per loop
$ python2.6 -m timeit 'map(lambda x:x.upper(),["a","b","c"])'
1000000 loops, best of 3: 1.87 usec per loop

4
Чи знаєте ви причину, чому розуміння списку швидше, ніж карта?
— Ніксуз

6
Це не завжди швидше. Ось приклад, коли це не так: stackoverflow.com/questions/1247486/… Але в цьому випадку це не набагато повільніше. Використання лямбда, очевидно, має велике значення. Є більше прикладів того, чому небезпечно довіряти своїй інтуїції з питань продуктивності, особливо в Python.
— Нед Дейлі

3
у python 3, mapвиграє гонку, але нічого не робить :)
— Жан-Франсуа Фабре

@NedDeily map(str.lower,["A","B","C"])найшвидший - python3.7.5
— SHIVAM JINDAL


20

Ознайомлення зі списком - як я це зробив, це "піфонічний" спосіб. Наступна стенограма показує, як перетворити список у верхній регістр, а потім назад у нижній:

pax@paxbox7:~$ python3
Python 3.5.2 (default, Nov 17 2016, 17:05:23) 
[GCC 5.4.0 20160609] on linux
Type "help", "copyright", "credits" or "license" for more information.

>>> x = ["one", "two", "three"] ; x
['one', 'two', 'three']

>>> x = [element.upper() for element in x] ; x
['ONE', 'TWO', 'THREE']

>>> x = [element.lower() for element in x] ; x
['one', 'two', 'three']

2
помилка, використання listв якості змінної імені не є найкращим вибором :)
— Жан-Франсуа Фабре

Ні, але, оскільки ім'я мало важливе для показаного методу, це не дуже актуально. Однак я зміню ім'я на випадок, якщо хтось хоче використовувати код таким, який є.
— paxdiablo

магія stackoverflow: 250 голосів за рішення єдиного пітона, використовуючи лямбда, де не повинно !! добре 249 зараз
— Жан-Франсуа Фабре

@ Jean-FrançoisFabre, не впевнений, чому ти вважаєш, що це рішення для Python-2. Як показує стенограма, вона чітко працює під Python 3.5.2. Насправді я просто перевірив це ще раз для підтвердження. ... проходить якийсь час, поки я розслідую ... Насправді, неважливо, здається, ви говорили про поточну прийняту відповідь, а не про цю, тому вам, мабуть, слід коментувати , а не тут. Без сумніву, чесна помилка. Ура.
— paxdiablo

1
так, я не критикував твоїх (окрім listречей :)) Де ти думаєш, звідки ви отримали УФ, який нещодавно отримали? :)
— Жан-Франсуа Фабре

7

Для цього зразка розуміння є найшвидшим

$ python -m timeit -s 's = ["один", "два", "три"] * 1000' '[x.upper for x in s]'
1000 петель, найкраще 3: 809 Usec на петлю

$ python -m timeit -s 's = ["один", "два", "три"] * 1000' 'карта (str.upper, s)'
1000 петель, найкраще 3: 1,12 мсек за петлю

$ python -m timeit -s 's = ["один", "два", "три"] * 1000' 'карта (лямбда x: x.upper (), s)'
1000 петель, найкраще 3: 1,77 мсек за петлю

5

студент запитує, інший студент із такою ж проблемою відповідає :))

fruits=['orange', 'grape', 'kiwi', 'apple', 'mango', 'fig', 'lemon']
newList = []
for fruit in fruits:
    newList.append(fruit.upper())
print(newList)

3
mylist = ['Mixed Case One', 'Mixed Case Two', 'Mixed Three']
print(list(map(lambda x: x.lower(), mylist)))
print(list(map(lambda x: x.upper(), mylist)))

2

Рішення:

>>> s = []
>>> p = ['This', 'That', 'There', 'is', 'apple']
>>> [s.append(i.lower()) if not i.islower() else s.append(i) for i in p]
>>> s
>>> ['this', 'that', 'there', 'is','apple']

Це рішення створить окремий список із малими елементами, незалежно від їх оригіналу. Якщо початковий регістр верхній, то list sзаголовок буде містити малі регістри відповідного елемента в list p. Якщо в початковому регістрі елемента списку вже є малі літери, list pто list sзастереження збереже корпус і збереже його в малому регістрі. Тепер ви можете використовувати list sзамість list p.


1

Якщо ваша мета полягає в узгодженні з іншим рядком шляхом перетворення за один прохід, ви також можете використовувати str.casefold().

Це корисно, якщо у вас є символи, які не мають права ascii, і збігаються з версіями ascii (наприклад, maße vs masse). Хоча str.lowerабо str.upperне вдасться в таких випадках str.casefold()пройти. Це доступно в Python 3, і ідея детально обговорюється з відповіддю https://stackoverflow.com/a/31599276/4848659 .

>>>str="Hello World";
>>>print(str.lower());
hello world
>>>print(str.upper());
HELLO WOLRD
>>>print(str.casefold());
hello world

1

Набагато простіше версія верхнього відповіді дається тут на @Amorpheuses.

З переліком значень у val:

valsLower = [item.lower() for item in vals]

Це добре працювало для мене із текстовим джерелом f = open ().


1

Ви можете спробувати скористатися:

my_list = ['india', 'america', 'china', 'korea']

def capitalize_list(item):
    return item.upper()

print(list(map(capitalize_list, my_list)))

0

Python3.6.8

In [1]: a = 'which option is the fastest'                                                                                                                                           

In [2]: %%timeit 
   ...: ''.join(a).upper() 
762 ns ± 11.4 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

In [3]: %%timeit  
   ...: map(lambda x:x.upper(), a) 
209 ns ± 5.73 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

In [4]: %%timeit  
   ...: map(str.upper, [i for i in a]) 
1.18 µs ± 11.3 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

In [5]: %%timeit 
   ...: [i.upper() for i in a] 
3.2 µs ± 64.1 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)

Якщо вам потрібен рядок або список як вихід, а не ітератор (це для Python3), порівняйте ''.join(string).upper()варіант із цим:

In [10]: %%timeit  
    ...: [i for i in map(lambda x:x.upper(), a)] 
4.32 µs ± 112 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)

0

Якщо ви намагаєтесь перетворити весь рядок у малі регістри списку, ви можете використовувати панди:

import pandas as pd

data = ['Study', 'Insights']

pd_d = list(pd.Series(data).str.lower())

вихід:

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