За генериране на нов списък от списък (масив), чиито елементи са низове, чрез извличане само на елементите на низовете, които отговарят на определени условия, или чрез извършване на замествания, преобразувания и т.н., се използва разбиране на списъци.
След кратко обяснение на разбирането на списъци, следващото съдържание е обяснено с примерен код.
- Извличане въз основа на това дали определен низ е включен или не (частично съвпадение)
- Замяна на определен низ
- Извличане, като започвате или не започвате с определен низ
- Извличане, като завършва или не завършва с определен низ
- Преценява се и се извлича по случаи
- Конвертиране на главни и малки букви
- Определя дали се използват буквени или цифрови знаци и ги извлича
- Множество условия
- (компютърен) регулярен израз
Обърнете внимание, че списъците могат да съхраняват различни типове данни и се различават строго от масивите. Ако искате да работите с масиви в процеси, които изискват размер на паметта и адреси в паметта или числена обработка на големи данни, използвайте array (стандартна библиотека) или NumPy.
- запис за включване в списък
- Съдържа определен низ (частично съвпадение) \ Не съдържа: in
- Замяна на определен низ
- Започва с определен низ \ не започва: startswith()
- Завършва с определен символен низ \ не завършва: endswith()
- Преценява се и се извлича по случаи
- Конвертиране на главни и малки букви
- Определя дали се използват буквени или цифрови знаци и ги извлича
- Множество условия
- (компютърен) регулярен израз
запис за включване в списък
Когато се генерира нов списък от списък, разбирането на списъци е по-просто за писане от циклите for.
[expression for any variable name in iterable object if conditional expression]
Ако елементът трябва да бъде избран само с условен израз, той не се обработва с израз, така че приема следната форма
[variable name for variable name in original list if conditional expression]
Ако условният израз if се превърне в условен израз if not, той се превръща в отрицание и елементите, които не удовлетворяват условния израз, могат да бъдат извлечени.
Съдържа определен низ (частично съвпадение) \ Не съдържа: in
В „специфичен низ в оригиналния низ“ връща True, ако оригиналният низ съдържа специфичния низ. Това е условен израз.
Отрицанието на in се прави с not in.
l = ['oneXXXaaa', 'twoXXXbbb', 'three999aaa', '000111222']
l_in = [s for s in l if 'XXX' in s]
print(l_in)
# ['oneXXXaaa', 'twoXXXbbb']
l_in_not = [s for s in l if 'XXX' not in s]
print(l_in_not)
# ['three999aaa', '000111222']
Замяна на определен низ
Ако искате да замените низ от елементи на списък, използвайте метода за заместване на низове replace() за всеки елемент в записа за разбиране на списък.
Ако няма низ, който да бъде заменен, не е необходимо да избирате елемента в условния израз if, тъй като той няма да бъде променен чрез прилагането на replace().
l_replace = [s.replace('XXX', 'ZZZ') for s in l]
print(l_replace)
# ['oneZZZaaa', 'twoZZZbbb', 'three999aaa', '000111222']
Ако искате да замените цял елемент, който съдържа определен низ, извлечете го с in и го обработете с тройния оператор. Тернарният оператор се записва в следната форма.True Value if Conditional Expression else False Value
Добре е, ако частта от израза на записа за разбиране на списък е троичен оператор.
l_replace_all = ['ZZZ' if 'XXX' in s else s for s in l]
print(l_replace_all)
# ['ZZZ', 'ZZZ', 'three999aaa', '000111222']
По-долу е представено обобщение на резултатите, посочени в скоби. Ако не сте свикнали да използвате скоби, може би ще ви е по-лесно да ги разберете и да избегнете грешки. От граматическа гледна точка няма проблем, дори ако пишете в скоби.
[('ZZZ' if ('XXX' in s) else s) for s in l]
Използването на in като условие е объркващо с нотацията за разбиране на списък in, но не е трудно, ако сте наясно със синтактичната форма на нотацията за разбиране на списък и троичните оператори.
Започва с определен низ \ не започва: startswith()
Методът за символни низове startswith() връща true, ако символният низ започва със символния низ, посочен в аргумента.
l_start = [s for s in l if s.startswith('t')]
print(l_start)
# ['twoXXXbbb', 'three999aaa']
l_start_not = [s for s in l if not s.startswith('t')]
print(l_start_not)
# ['oneXXXaaa', '000111222']
Завършва с определен символен низ \ не завършва: endswith()
Методът endswith() връща true, ако низът завършва с низа, посочен в аргумента.
l_end = [s for s in l if s.endswith('aaa')]
print(l_end)
# ['oneXXXaaa', 'three999aaa']
l_end_not = [s for s in l if not s.endswith('aaa')]
print(l_end_not)
# ['twoXXXbbb', '000111222']
Преценява се и се извлича по случаи
Методите за символни низове isupper(),islower() могат да се използват, за да се определи дали даден низ е изцяло с главни или изцяло с малки букви.
l_lower = [s for s in l if s.islower()]
print(l_lower)
# ['three999aaa']
Конвертиране на главни и малки букви
Ако искате да преобразувате всички символи в големи или малки букви, използвайте методите за низ upper() и lower(). Други методи са capitalize(), който изписва само първата буква, и swapcase(), който разменя главни и малки букви.
Както в примера за заместване по-горе, използвайте тройния оператор, ако искате да обработите само елементите, които отговарят на условието.
l_upper_all = [s.upper() for s in l]
print(l_upper_all)
# ['ONEXXXAAA', 'TWOXXXBBB', 'THREE999AAA', '000111222']
l_lower_to_upper = [s.upper() if s.islower() else s for s in l]
print(l_lower_to_upper)
# ['oneXXXaaa', 'twoXXXbbb', 'THREE999AAA', '000111222']
Определя дали се използват буквени или цифрови знаци и ги извлича
Методите isalpha() и isnumeric() могат да се използват, за да се определи дали даден низ е изцяло буквен, цифров и т.н.
l_isalpha = [s for s in l if s.isalpha()]
print(l_isalpha)
# ['oneXXXaaa', 'twoXXXbbb']
l_isnumeric = [s for s in l if s.isnumeric()]
print(l_isnumeric)
# ['000111222']
Множество условия
Частта на условния израз в списъците за разбиране може да съдържа няколко условия. Могат да се използват и отрицателни условия „не“.
Когато използвате три или повече условни израза, е по-безопасно да заградите всяка група в скоби (), тъй като резултатът ще варира в зависимост от реда.
l_multi = [s for s in l if s.isalpha() and not s.startswith('t')]
print(l_multi)
# ['oneXXXaaa']
l_multi_or = [s for s in l if (s.isalpha() and not s.startswith('t')) or ('bbb' in s)]
print(l_multi_or)
# ['oneXXXaaa', 'twoXXXbbb']
(компютърен) регулярен израз
Регулярните изрази позволяват изключително гъвкава обработка.
Обектът на съвпадение, върнат от re.match(), когато съвпада, винаги се определя като true, когато се оценява с условен израз. Ако не съвпада, той връща None, което е false в условния израз. Така че, ако искате да извлечете само елементите, които съвпадат с регулярния израз, просто приложете re.match() към частта с условния израз на израза за разбиране на списъка, както преди.
import re
l = ['oneXXXaaa', 'twoXXXbbb', 'three999aaa', '000111222']
l_re_match = [s for s in l if re.match('.*XXX.*', s)]
print(l_re_match)
# ['oneXXXaaa', 'twoXXXbbb']
Полезна е и функцията re.sub(), която замества съвпадащата част от регулярен израз. За да извлечете и замените само съвпадащите елементи, просто добавете „if conditional expression“.
l_re_sub_all = [re.sub('(.*)XXX(.*)', r'\2---\1', s) for s in l]
print(l_re_sub_all)
# ['aaa---one', 'bbb---two', 'three999aaa', '000111222']
l_re_sub = [re.sub('(.*)XXX(.*)', r'\2---\1', s) for s in l if re.match('.*XXX.*', s)]
print(l_re_sub)
# ['aaa---one', 'bbb---two']