<?php
$selfClosing = explode(',', 'area,base,basefont,br,col,frame,hr,img,input,isindex,link,meta,param,embed');
$html = '
<p><a href="#">foo</a></p>
<hr/>
<br/>
<div>name</div>';
$dom = new DOMDocument();
$dom->loadHTML($html);
$els = $dom->getElementsByTagName('*');
foreach ( $els as $el ) {
$nodeName = strtolower($el->nodeName);
if ( !in_array( $nodeName, $selfClosing ) ) {
var_dump( $nodeName );
}
}
Выход:
string(4) "html"
string(4) "body"
string(1) "p"
string(1) "a"
string(3) "div"
В основном просто определяют имена узлов узлов, которые закрываются самостоятельно, загружают всю строку html в библиотеку DOM, захватывают все элементы, перебирают и отфильтровывают которые не закрываются и не работают на них.
Я уверен, что вы уже знаете, что вам не следует использовать регулярное выражение для этой цели.
Один из способов состоит в том, чтобы напечатать оба числа, когда вы обнаружили, что они являются последовательными, но также проверить, что номер по индексу i-1
не был в последовательном списке, так что номер по индексу i
не печатается дважды:
num = [8, 9, 4, 1, 2, 3]
for i in range(len(num)-1): # not using -1 will cause index error
if num[i] + 1 == num[i + 1]:
if i == 0 or (i - 1 >= 0 and num[i - 1] != num[i] - 1):
print('Con', num[i])
print('Con', num[i + 1])
Можно попробовать и с более сложным списком:
num = [8, 9, 4, 1, 2, 3, 4, 4, 8, 9, 1, 2, 3, 0, 1, 5, 6, 1]
for i in range(len(num)-1): # not using -1 will cause index error
if num[i] + 1 == num[i + 1]:
if i == 0 or (i - 1 >= 0 and num[i - 1] != num[i] - 1):
print('Con', num[i])
print('Con', num[i + 1])
Ваш код проверяется только в одном направлении (после него следует порядковый номер) Для полной последовательности вы должны проверить в обоих направлениях.
num=[8,9,4,1,2,3]
assert(len(num) > 1)
for i, n in enumerate(num):
if i != 0:
if n == num[i-1] + 1:
print("Con", n)
continue
if i != len(num) - 1:
if n == num[i+1] - 1:
print("Con", n)
num = [8, 9, 4, 1, 2, 3]
def con(rng, pos=0):
if pos < len(rng):
if (pos > 0 and rng[pos]-1 == rng[pos-1]) or (pos < len(rng) -1 and rng[pos]+1 == rng[pos+1]):
print("con", rng[pos])
con(rng, pos+1)
con(num)
редактировать: это решение основано на параллельной функции и требует только список в качестве аргумента. Пока они находятся в пределах нижней / верхней границы списка, функция будет проверять, равны ли (предыдущее число) -1 или (следующее число) +1 (это число): con 8 con 9 con 1 con 2 con 3
Это потому, что вы проверяете только следующий номер. Если вам нужен второй номер (например, 9 или 3), вы должны также включить проверку для предыдущего номера. Это сделает if
немного длиннее, но это сработает.
num=[8,9,4,1,2,3]
for i in range(len(num)):
if (
( # check for the next number
i + 1 != len (num) and # don't check the end of the list
num[i]+1==num[i+1]
) or ( # check for the previous number
i != 0 and # don't check before the list
num [i-1] == num [i] - 1
)
): print('Con',num[i])
Кроме того, мне пришлось убрать -1
в вашем диапазоне, потому что я уже делаю ручную проверку, и, как указывалось, это показало 3 из показа.
Вы можете использовать функцию groupby()
:
from itertools import groupby
from operator import sub, itemgetter
num = [8, 9, 4, 1, 2, 3]
iget = itemgetter(1)
gb = groupby(enumerate(num), key=lambda x: sub(*x))
all_groups = (list(map(iget, g)) for _, g in gb)
list(filter(lambda x: len(x) > 1, all_groups))
# [[8, 9], [1, 2, 3]]
.