python数据科学(1)

1. 字典

# 1. 加载一个句子到变量中
sentence = "Peter Piper picked a pech of pickled peppers A peck of pickled \
peppers Peter Piper picked If Peter Piper picked a peck of picked \
peppers Wheres the peck of pickled peppers Peter Piper Piper picked"

# 2. 初始化一个字典对象
word_dict = {}

# 3. 执行对词频的统计

## 3.1. 法一
# for word in sentence.split():
#     if word not in word_dict:
#         word_dict[word] = 1
#     else:
#         word_dict[word] += 1

# 3.2. 法二
for word in sentence.split():
    word_dict.setdefault(word, 0)
    word_dict[word] += 1
    

# 4. 打印输出词频结果
print(word_dict)
{'Peter': 4, 'Piper': 5, 'picked': 5, 'a': 2, 'pech': 1, 'of': 4, 'pickled': 3, 'peppers': 4, 'A': 1, 'peck': 3, 'If': 1, 'Wheres': 1, 'the': 1}
from collections import defaultdict

sentence = "Peter Piper picked a pech of pickled peppers A peck of pickled \
peppers Peter Piper picked If Peter Piper picked a peck of picked \
peppers Wheres the peck of pickled peppers Peter Piper Piper picked"

word_dict = defaultdict(int)

for word in sentence.split():
    word_dict[word] += 1

print(word_dict)
defaultdict(<class 'int'>, {'Peter': 4, 'Piper': 5, 'picked': 5, 'a': 2, 'pech': 1, 'of': 4, 'pickled': 3, 'peppers': 4, 'A': 1, 'peck': 3, 'If': 1, 'Wheres': 1, 'the': 1})
for key, value in word_dict.items():
    print(key, value)
Peter 4
Piper 5
picked 5
a 2
pech 1
of 4
pickled 3
peppers 4
A 1
peck 3
If 1
Wheres 1
the 1
from collections import Counter

sentence = "Peter Piper picked a pech of pickled peppers A peck of pickled \
peppers Peter Piper picked If Peter Piper picked a peck of picked \
peppers Wheres the peck of pickled peppers Peter Piper Piper picked"

words = sentence.split()

word_count = Counter(words)

print(word_count)
Counter({'Piper': 5, 'picked': 5, 'Peter': 4, 'of': 4, 'peppers': 4, 'pickled': 3, 'peck': 3, 'a': 2, 'pech': 1, 'A': 1, 'If': 1, 'Wheres': 1, 'the': 1})
# 展示”字典的字典“
from collections import defaultdict

user_movie_rating = defaultdict(lambda: defaultdict(int))

# 初始化爱丽丝的评分
user_movie_rating["Alice"]["LOR1"] = 4
user_movie_rating["Alice"]["LOR2"] = 5
user_movie_rating["Alice"]["LOR3"] = 3
user_movie_rating["Alice"]["SW1"] = 5
user_movie_rating["Alice"]["SW2"] = 3

print(user_movie_rating)
defaultdict(<function <lambda> at 0x10f176598>, {'Alice': defaultdict(<class 'int'>, {'LOR1': 4, 'LOR2': 5, 'LOR3': 3, 'SW1': 5, 'SW2': 3})})

2. 元组

# 1. 创建一个元组

a_tuple = (1, 2, 'a')
b_tuple = 1, 2, 'a'

# 2. 利用索引访问元组的元素
print(b_tuple[0])
print(b_tuple[-1])

# 3. 元组的元素无法修改元素值
try:
    b_tuple[0] = 20
except:
    print("Cannot change value of tuple by index")

# 4. 元组的元素的元素可变,如元组的元素是一个列表
c_tuple = (1, 2, [10, 20, 100])
c_tuple[2][0] = 100
print(c_tuple)

# 5. 元组不能扩展,但是可以串联
print(a_tuple + b_tuple)

# 6. 对元组进行切片
a = (1, 2, 3, 4, 5, 6, 7, 8, 9)
print(a[1:])
print(a[1:3])
print(a[1:6:2])
print(a[:-1])

# 7. 对元组求 min 和 max 值
print(min(a), max(a))

# 8. 包含于与非包含于
if 1 in a:
    print("Element 1 is available in tuple a")
else:
    print("Element 1 is inavalable in tuple a")
    
    
# 从数据中生成特征值时,创建特征值元组,避免数值被下游数组改变

# 用元组串联不同模块生成的不同特征值,得到完整的特征值向量

# 元组因不可变,可作为字典的键

# 9. 命名元组

from collections import namedtuple

vector = namedtuple("Dimention", 'x y z')
vec_1 = vector(1, 1, 1)
vec_2 = vector(1, 0, 1)

manhattan_distance = abs(vec_1.x - vec_2.x) + abs(vec_1.y - vec_2.y) + abs(vec_1.z - vec_2.z)

print("Manhattan distance between vectors = %d" % (manhattan_distance))
1
a
Cannot change value of tuple by index
(1, 2, [100, 20, 100])
(1, 2, 'a', 1, 2, 'a')
(2, 3, 4, 5, 6, 7, 8, 9)
(2, 3)
(2, 4, 6)
(1, 2, 3, 4, 5, 6, 7, 8)
1 9
Element 1 is available in tuple a
Manhattan distance between vectors = 1

3. 集合

# 1. 初始化两个句子
st_1 = "dogs chase cats"
st_2 = "dogs hate cats"

# 2. 从字符串中创建集合
st_1_wrds = set(st_1.split())
st_2_wrds = set(st_2.split())

# 3. 找出每个集合中不重复词的总数,即词表大小
no_wrds_st_1 = len(st_1_wrds)
no_wrds_st_2 = len(st_2_wrds)

# 4. 集合并集
cmn_wrds = st_1_wrds.intersection(st_2_wrds)
no_cmn_wrds = len(cmn_wrds)

# 5. 集合不重复的词
unq_wrds = st_1_wrds.union(st_2_wrds)
no_unq_wrds = len(unq_wrds)

# 6. 计算 Jaccard 相似度
similarity = no_cmn_wrds / (1.0 * no_unq_wrds)

# 7. 打印输出
print("No words in sent_1 = %d" % (no_wrds_st_1))
print("No words in sent_2 = %d" % (no_wrds_st_2))
print("Sentence 1 words = ", st_1_wrds)
print("Sentence 2 words = ", st_2_wrds)
print("No words in common = %d" % (no_cmn_wrds))
print("Common words = ", cmn_wrds)
print("Total unique words = %d" % (no_unq_wrds))
print("Unique words = ", unq_wrds)
print("Similarity = No words in common / No unique words, %d/%d \
 = %.2f" %(no_cmn_wrds, no_unq_wrds, similarity))

No words in sent_1 = 3
No words in sent_2 = 3
Sentence 1 words =  {'cats', 'dogs', 'chase'}
Sentence 2 words =  {'cats', 'dogs', 'hate'}
No words in common = 2
Common words =  {'cats', 'dogs'}
Total unique words = 4
Unique words =  {'dogs', 'chase', 'cats', 'hate'}
Similarity = No words in common / No unique words, 2/4  = 0.50
# 从 scikit-learn 的库中使用内置函数
from sklearn.metrics import jaccard_similarity_score

st_1 = "dogs chase cats"
st_2 = "dogs hate cats"

# 从字符串中创建词的集合
st_1_wrds = set(st_1.split())
st_2_wrds = set(st_2.split())
unq_wrds = st_1_wrds.union(st_2_wrds)

a = [ 1 if w in st_1_wrds else 0 for w in unq_wrds]
b = [ 1 if w in st_2_wrds else 0 for w in unq_wrds]

print(a)
print(b)
print(jaccard_similarity_score(a, b))
[1, 1, 1, 0]
[1, 0, 1, 1]
0.5


/Users/apple/anaconda3/lib/python3.7/site-packages/sklearn/metrics/classification.py:635: DeprecationWarning: jaccard_similarity_score has been deprecated and replaced with jaccard_score. It will be removed in version 0.23. This implementation has surprising behavior for binary and multiclass classification tasks.
  'and multiclass classification tasks.', DeprecationWarning)

4. 列表

# 1. 快速创建一个列表
a = range(1, 10)
print(a)
b = ["a", "b", "c"]
print(b)

# 2. 索引访问
# 3. 负数作为索引
# 4. 使用两个索引参数, 切片操作访问列表的子集

# 5. 列表串联(需要类型相同)
a = [1, 2, 3]
b = [5, 6, 7]
print(a + b)
print(min(a), max(b))

# 包含于、非包含于

# 8. 追加和扩展列表
a = list(range(1, 10))
a.append(100)
a

# 9. 列表实现堆
a_stack = []
a_stack.append(1)
a_stack.append(2)
a_stack.append(3)

print(a.pop())
print(a.pop())

# 10. 列表实现队列
a_queue = []
a_queue.append(1)
a_queue.append(2)
a_queue.append(3)

print(a.pop(0))
print(a.pop(0))

# 11. 列表排序和反转
from random import shuffle
a = list(range(1, 20))
shuffle(a)
print(a)

a.sort()
print(a)

a.reverse()
print(a)
range(1, 10)
['a', 'b', 'c']
[1, 2, 3, 5, 6, 7]
1 7
100
9
1
2
[4, 7, 1, 8, 14, 6, 19, 13, 3, 16, 5, 12, 15, 11, 17, 2, 9, 10, 18]
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19]
[19, 18, 17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1]

5. 列表推导

# 1. 序列,表示一个对其元素感兴趣的列表
# 2. 序列的元素拥有可变的表示方法
# 3. 使用输入序列的元素来产生输出表达式,
# 4. 一个可选的谓语表达式

# 1. 定义’
a = [1, 2, -1, -2, 3, 4, -3, -4]
b = [pow(x, 2) for x in a if x < 0]
print(b)

a = {'a':1, 'b':2, 'c':3}
b = {x:pow(y, 2) for x,y in a.items()}
print(b)

def process(x):
    if isinstance(x, str):
        return x.lower()
    elif isinstance(x, int):
        return x*x
    else:
        return -9
    
a = (1, 2, -1, -2, 'D', 3, 4, -3, 'A')
b = tuple(process(x) for x in a)
print(b)
[1, 4, 9, 16]
{'a': 1, 'b': 4, 'c': 9}
(1, 4, 1, 4, 'd', 9, 16, 9, 'a')

6. 迭代器

如何访问数据、理解数据格式、依次传送数据、给调用者需要的数据

# 1. 简单的迭代器
class SimpleCounter(object):
    def __init__(self, start, end):
        self.current = start
        self.end = end
    def __iter__(self):
        'returns itself as an iterator object'
        return self
    def __next__(self):
        'Returns the next value till current is lower than end'
        if self.current > self.end:
            raise StopIteration
        else:
            self.current += 1
            return self.current - 1
# # 2. 访问一
c = SimpleCounter(1, 3)
# print(c.next())
# print(c.next())
# print(c.next())
# print(c.next())

# 3. 访问二
for entry in iter(c):
    print(entry)
1
2
3
# 1. 在python中,一个文件对象就是一个迭代器,支持iter(), next()
# f = open(some_file_of_interest)
# for l in iter(f):
#     print(l)
# f.close()
# more:itertools 中的 count(), cycle(),以及, repeat()

7. 生成一个迭代器和生成器

# 生成器 + 可迭代 ——》 迭代器
SimpleCounter = (x**2 for x in range(1, 10))

tot = 0
for val in SimpleCounter:
    tot += val
    
print(tot)
285
def my_gen(low, high):
    for x in range(low, high):
        yield x**2
tot = 0
for val in my_gen(1, 10):
    tot += val
print(tot)

# 使用生成器对象时,只能访问序列一次
gen = (x**2 for x in range(1, 10))

for val in iter(gen):
    print(val)
285
1
4
9
16
25
36
49
64
81

8. 可迭代对象

# 可迭代对象与生成器:是否可重复访问
# 不保持任何状态——基于对象的生成器
# 所有带有 iter 方法的类,产生数据时,可作为无状态对象生成器来使用

# 1. 先创建一个简单的带有 iter 方法的类
class SimpleIterable(object):
    def __init__(self, start, end):
        self.start = start
        self.end = end 
    def __iter__(self):
        for x in range(self.start, self.end):
            yield x ** 2
            
# 2. 现在调用这个类,并且迭代他的值两次
c = SimpleIterable(1, 10)

tot = 0
for val in iter(c):
    tot += val
print(tot)

tot = 0
for val in iter(c):
    tot += val
print(tot)
285
285

9. 将函数作为变量传递–在一个函数中定义一个函数

# 除了命令范式,,Python支持函数式编程
# 1. 定义一个简单的函数
def square_input(x):
    return x * x
square_me = square_input
print(square_me(6))

# 1. 定义一个函数
def sum_square(x):
    def square_input(x):
        return x*x
    return sum([square_input(x1) for x1 in x])
print(sum_square([2, 4, 5]))

# 函数作为参数传递
from math import log

def square_input(x):
    return x*x

# 1. 定义一个类函数,将另一个函数作为输入
# 并将它应用到给定的输入序列上
def apply_func(func_x, input_x):
    return map(func_x, input_x)

# 2. 使用函数,校验结果
a = [2, 3, 4]
print(list(apply_func(square_input, a)))
print(list(apply_func(log, a)))
36
45
[4, 9, 16]
[0.6931471805599453, 1.0986122886681098, 1.3862943611198906]

10. 返回一个函数

# 1. 定义一个简单的函数来演示在函数中返回函数的概念
def cylinder_vol(r):
    pi = 3.141
    def get_vol(h):
        return pi * r ** 2 * h
    return get_vol

# 2. 定义一个固定的半径值,在此给定半径和任意高度条件下,写一个函数确定体积
radius = 10
find_volume = cylinder_vol(radius)

# 3. 给出不同的高度,求解圆柱体的体积
height = 10
print("Volume of cylinder of fradius %d and height %d = %.2f cubic units" % (radius, height, find_volume(height)))

height = 20
print("Volume of cylinder of fradius %d and height %d = %.2f cubic units" % (radius, height, find_volume(height)))

# more: Functools,高阶函数模块
Volume of cylinder of fradius 10 and height 10 = 3141.00 cubic units
Volume of cylinder of fradius 10 and height 20 = 6282.00 cubic units
# 使用装饰器改变函数行为
from string import punctuation
def pipeline_wrapper(func):
    # pipeline_wrapper 返回了 wrapper 函数, 后者中,最后的返回语句返回 func , 传递给 wrapper 的原始函数
    # wrapper 改变了原来的pipeline_wrapper 的行为
    def to_lower(x):
        return x.lower()
    
    def remove_punc(x):
        for p in punctuation:
            x = x.replace(p, ' ')
        return x
    
    def wrapper(*args, **kwargs):
        x = to_lower(*args, **kwargs)
        x = remove_punc(x)
        return func(x)
    return wrapper

# 简便的方式调用
# tokenize_whitespace = pipeline_wrapper (clean_tokens)
@pipeline_wrapper
def tokenize_whitespace(inText):
    return inText.split()

s = "string. With. Punctuation?"
print(tokenize_whitespace(s))

['string', 'with', 'punctuation']

11. 匿名函数

# 1. 创建列表
a = [10, 20, 30]
def do_list(a_list, func):
    total = 0
    for element in a_list:
        total += func(element)
    return total

print(do_list(a, lambda x:x**2))
print(do_list(a, lambda x:x**3))

b = [lambda x: x%3 == 0 for x in a]
print(b)
1400
36000
[<function <listcomp>.<lambda> at 0x11b4fe048>, <function <listcomp>.<lambda> at 0x11b4fe0d0>, <function <listcomp>.<lambda> at 0x11b4fe158>]

12. 映射函数 map

使用函数,和一个可迭代对象作为参数

a = [10, 20, 30]
print(sum(map(lambda x:x**2, a)))
b = [1, 2, 3]
print(list(map(pow, a, b)))
1400
[10, 400, 27000]

13. 过滤器

按照给定的函数,从序列做过滤相应的元素

使用函数,和一个可迭代对象作为参数

a = [10, 20, -10, 30, 40, 50]
print(list(filter(lambda x:x>10, a)))
[20, 30, 40, 50]

14. zip 与 izip 函数

izip将两个相同长度的集合合并成对

print(list(zip(range(1, 5), range(1, 5))))

a = (2, 3)
print(pow(*a))
# * 将集合中每个元素作为位置参数进行传递

a_dict = {"x":10, "y":10, "z":10, "x1":10, "y1":10, "z1":10}
def dist(x,y,z,x1,y1,z1):
    return abs((x-x1) + (y-y1) + (z-z1))
print(dist(**a_dict))

# * 使得可接受的参数变量个数不在受限
def any_sum(*args):
    tot = 0
    for arg in args:
        tot += arg
    return tot

print(any_sum(1, 2))
print(any_sum(1, 2, 2, 3, 4))

# 某些情形,不知道传递什么样子的参数
# more:izip 需要的时候才会计算,属于 itertools 模块
[(1, 1), (2, 2), (3, 3), (4, 4)]
8
0
3
12

15. 从数据表格使用数组

如何高效的读取外部数据,并将之转化为numpy数组,方便后续的数据处理

# 1. 先用 StringIO 来模拟一个小型的表格数据
import numpy as np
from io import StringIO
in_data = StringIO("10, 20, 30\n56, 89, 90\n33, 46, 89")

# 2. 使用 NumPy 的 genfromtxt 来读取数据,并创建一个 Numpy 数组
data = np.genfromtxt(in_data, dtype = int, delimiter = ",")
print(data)

# 3. 清除掉一些我们不需要的列
in_data = StringIO("10, 20, 30\n56, 89, 90\n33, 46, 89")
data = np.genfromtxt(in_data, dtype = int, delimiter = ",", usecols = (0, 1))
print(data)

# 4. 设置列名
in_data = StringIO("10, 20, 30\n56, 89, 90\n33, 46, 89")
data = np.genfromtxt(in_data, dtype = int, delimiter = ",", names = "a, b, c")
print(data)

# 5. 使用列名来处理数据
in_data = StringIO("a, b, c\n10, 20, 30\n56, 89, 90\n33, 46, 89")
data = np.genfromtxt(in_data, dtype = int, delimiter = ",", names = True)
# 避免签到或后导的空格没有被完全处理:设置参数:autostrip = true;
# 跳过最开始的 n 行:skip_header = n
# 跳过最后的 n 行:skip_footer = n
data
# more:loadtxt(不需要复杂的数据处理架构,不需要处理丢失的数据)
# more:csv.Sniffer.sniff(只想把数据加载到列表中)
[[10 20 30]
 [56 89 90]
 [33 46 89]]
[[10 20]
 [56 89]
 [33 46]]
[(10, 20, 30) (56, 89, 90) (33, 46, 89)]





array([(10, 20, 30), (56, 89, 90), (33, 46, 89)],
      dtype=[('a', '<i8'), ('b', '<i8'), ('c', '<i8')])

16. 队列进行预处理

import numpy as np
from io import StringIO
in_data = StringIO("30kg,inr2000,31.11,56.33,1\n52kg,inr8000.35,12,16.7,2")
data = np.genfromtxt(in_data,delimiter = ',')
data

# 1. 使用lambda函数定两个数据预处理函数
# 此处会报错:a bytes-like object is required, not 'str'
strip_func_1 = lambda x:float(str(x,encoding='utf-8').rstrip("kg"))
strip_func_2 = lambda x:float(str(x,encoding='utf-8').lstrip("inr"))

# 2. 创建一个函数的字典
convert_funcs = {0:strip_func_1, 1:strip_func_2}

# 3. 将这个函数的字典传递给 genfromtxt
in_data = StringIO("30kg,inr2000,31.11,56.33,1\n52kg,inr8000.35,12,16.7,2")
data = np.genfromtxt(in_data, delimiter = ",", converters = {0:strip_func_1, 1:strip_func_2})
print(data)

# 4. 使用lambda函数来处理转换过程
in_data = StringIO("10,20,30\n56,,90\n33,46,89")
mss_func = lambda x : float(x.strip() or -999)
data = np.genfromtxt(in_data, delimiter = ",", converters = {1:mss_func})
print(data)
[[3.00000e+01 2.00000e+03 3.11100e+01 5.63300e+01 1.00000e+00]
 [5.20000e+01 8.00035e+03 1.20000e+01 1.67000e+01 2.00000e+00]]
[[  10.   20.   30.]
 [  56. -999.   90.]
 [  33.   46.   89.]]

17. 列表排序

a = [8, 0, 3, 4, 5, 2, 9, 6, 7, 1]
b = [8, 0, 3, 4, 5, 2, 9, 6, 7, 1]
print(a)
a.sort()
# 只对列表数据类型有效
print(a)
print(b)
# 可用于其他可迭代类型
b_s = sorted(b)
print(b_s)
[8, 0, 3, 4, 5, 2, 9, 6, 7, 1]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
[8, 0, 3, 4, 5, 2, 9, 6, 7, 1]
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]

18. 采用键排序

# 1. 首先创建一个元组组成的列表用来测试排序
employee_records = [('joe', 1, 53), ('beck', 2, 26),\
                    ('ele', 6, 32), ('neo', 3, 45), \
                    ('christ', 5, 33), ('trinity', 4, 29),\
                   ]

# 2. 使用雇员名字进行排序
print(sorted(employee_records, key = lambda x:x[0]))

# 3. 使用雇员 ID 进行排序
print(sorted(employee_records, key = lambda x:x[1]))

# Python 提供快捷函数访问键
from operator import itemgetter
employee_records = [('joe', 1, 53), ('beck', 2, 26),\
                    ('ele', 6, 32), ('neo', 3, 45), \
                    ('christ', 5, 33), ('trinity', 4, 29),\
                   ]
print(sorted(employee_records, key = itemgetter(1)))
print(sorted(employee_records, key = itemgetter(0, 1)))

# 若可迭代对象里的元素是类对象
# 则可以用 attrgetter 和 methodcaller

class employee(object):
    def __init__(self, name, id, age):
        self.name = name
        self.id = id
        self.age = age
    def pretty_print(self):
        print(self.name, self.id, self.age)
    def random_method(self):
        return self.age / self.id
    

# 将类对象填入列表
employee_records = []
emp1 = employee('joe', 1, 53)
emp2 = employee('beck', 2, 26)
emp3 = employee('ele', 6, 32)

employee_records.append(emp1)
employee_records.append(emp2)
employee_records.append(emp3)

# 打印输出记录
for emp in employee_records:
    emp.pretty_print()

from operator import attrgetter
employee_records_sorted = sorted(employee_records, key = attrgetter('age'))

for emp in employee_records_sorted:
    emp.pretty_print()
    
from operator import methodcaller
employee_records_sorted = sorted(employee_records, key = methodcaller('random_method'))
for emp in employee_records_sorted:
    emp.pretty_print()
[('beck', 2, 26), ('christ', 5, 33), ('ele', 6, 32), ('joe', 1, 53), ('neo', 3, 45), ('trinity', 4, 29)]
[('joe', 1, 53), ('beck', 2, 26), ('neo', 3, 45), ('trinity', 4, 29), ('christ', 5, 33), ('ele', 6, 32)]
[('joe', 1, 53), ('beck', 2, 26), ('neo', 3, 45), ('trinity', 4, 29), ('christ', 5, 33), ('ele', 6, 32)]
[('beck', 2, 26), ('christ', 5, 33), ('ele', 6, 32), ('joe', 1, 53), ('neo', 3, 45), ('trinity', 4, 29)]
joe 1 53
beck 2 26
ele 6 32
beck 2 26
ele 6 32
joe 1 53
ele 6 32
beck 2 26
joe 1 53

19. 使用itertools

# 1. 加载库文件
from itertools import chain, compress, combinations, count, islice, zip_longest
# 1. 链的演示,组合不同的可迭代对象
a = [1, 2, 3]
b = ['a', 'b', 'c']
print(list(chain(a, b)))

# 2. 压缩实例,一个数据筛选器,基于第二个对象对于第一个对象中的数据进行筛选
a = [1, 2, 3]
b = [1, 0, 1]
print(list(compress(a, b)))

# 3. 对给定的列表,返回长度为n的子序列
a = [1, 2, 3, 4]
print(list(combinations(a, 2)))

# 4. 给定一个起始整数,产生连续的整数
a = range(5)
b = zip(count(1), a)
for element in b:
    print(element)
    
a = range(100)
b = islice(a, 0, 100, 2)
print(list(b))
[1, 2, 3, 'a', 'b', 'c']
[1, 3]
[(1, 2), (1, 3), (1, 4), (2, 3), (2, 4), (3, 4)]
(1, 0)
(2, 1)
(3, 2)
(4, 3)
(5, 4)
[0, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 28, 30, 32, 34, 36, 38, 40, 42, 44, 46, 48, 50, 52, 54, 56, 58, 60, 62, 64, 66, 68, 70, 72, 74, 76, 78, 80, 82, 84, 86, 88, 90, 92, 94, 96, 98]
发布了182 篇原创文章 · 获赞 101 · 访问量 20万+

猜你喜欢

转载自blog.csdn.net/lancecrazy/article/details/102632393
今日推荐