Python培训教程:Day16-20Python语言进阶

Python培训教程:Python语言进阶

数据结构和算法

算法:解决问题的方法和步骤

评价算法的好坏:渐近时间复杂度和渐近空间复杂度。

渐近时间复杂度的大O标记:

  • 常量时间复杂度 - 布隆过滤器 / 哈希存储
  • 对数时间复杂度 - 折半查找(二分查找)
  • 线性时间复杂度 - 顺序查找 / 桶排序
  • 对数线性时间复杂度 - 高级排序算法(归并排序、快速排序)
  • 平方时间复杂度 - 简单排序算法(选择排序、插入排序、冒泡排序)
  • 立方时间复杂度 - Floyd算法 / 矩阵乘法运算
  • 几何级数时间复杂度 - 汉诺塔
  • 阶乘时间复杂度 - 旅行经销商问题 - NP

排序算法(选择、冒泡和归并)和查找算法(顺序和折半)

def select_sort(origin_items, comp=lambda x, y: x < y):
    """简单选择排序"""
    items = origin_items[:]
    for i in range(len(items) - 1):
        min_index = i
        for j in range(i + 1, len(items)):
            if comp(items[j], items[min_index]):
                min_index = j
        items[i], items[min_index] = items[min_index], items[i]
    return items
def bubble_sort(origin_items, comp=lambda x, y: x > y):
    """高质量冒泡排序(搅拌排序)"""
    items = origin_items[:]
    for i in range(len(items) - 1):
        swapped = False
        for j in range(i, len(items) - 1 - i):
            if comp(items[j], items[j + 1]):
                items[j], items[j + 1] = items[j + 1], items[j]
                swapped = True
        if swapped:
            swapped = False
            for j in range(len(items) - 2 - i, i, -1):
                if comp(items[j - 1], items[j]):
                    items[j], items[j - 1] = items[j - 1], items[j]
                    swapped = True
        if not swapped:
            break
    return items
def merge_sort(items, comp=lambda x, y: x <= y):
    """归并排序(分治法)"""
    if len(items) < 2:
        return items[:]
    mid = len(items) // 2
    left = merge_sort(items[:mid], comp)
    right = merge_sort(items[mid:], comp)
    return merge(left, right, comp)


def merge(items1, items2, comp):
    """合并(将两个有序的列表合并成一个有序的列表)"""
    items = []
    index, index2 = 0, 0
    while index1 < len(items1) and index2 < len(items2):
        if comp(items1[index1], items2[index2]):
            items.append(items1[index1])
            index1 += 1
        else:
            items.append(items2[index2])
            index2 += 1
    items += items1[index1:]
    items += items2[index2:]
    return items
def seq_search(items, key):
    """顺序查找"""
    for index, item in enumerate(items):
        if item == key:
            return index
    return -1
def bin_search(items, key):
    """折半查找"""
    start, end = 0, len(items) - 1
    while start <= end:
        mid = (start + end) // 2
        if key > items[mid]:
            start = mid + 1
        elif key < items[mid]:
            end = mid - 1
        else:
            return mid
    return -1

使用生成式(推导式)语法

prices = {
    'AAPL': 191.88,
    'GOOG': 1186.96,
    'IBM': 149.24,
    'ORCL': 48.44,
    'ACN': 166.89,
    'FB': 208.09,
    'SYMC': 21.29
}

用股票价格大于100元的股票构造一个新的字典
prices2 = {key: value for key, value in prices.items() if value > 100}
print(prices2)
说明:生成式(推导式)可以用来生成列表、集合和字典。

嵌套的列表

names = [‘关羽’, ‘张飞’, ‘赵云’, ‘马超’, ‘黄忠’]
courses = [‘语文’, ‘数学’, ‘英语’] 录入五个学生三门课程的成绩
错误 - 参考http://pythontutor.com/visualize.html#mode=edit scores = [[None] * len(courses)] * len(names)
scores = [[None] * len(courses) for _ in range(len(names))]
for row, name in enumerate(names):
for col, course in enumerate(courses):
scores[row][col] = float(input(f’请输入{name}的{course}成绩: '))
print(scores)
Python Tutor - VISUALIZE CODE AND GET LIVE HELP

heapq、itertools等的用法

“”"
从列表中找出最大的或最小的N个元素
堆结构(大根堆/小根堆)

"""
import heapq

list1 = [34, 25, 12, 99, 87, 63, 58, 78, 88, 92]
list2 = [
    {'name': 'IBM', 'shares': 100, 'price': 91.1},
    {'name': 'AAPL', 'shares': 50, 'price': 543.22},
    {'name': 'FB', 'shares': 200, 'price': 21.09},
    {'name': 'HPQ', 'shares': 35, 'price': 31.75},
    {'name': 'YHOO', 'shares': 45, 'price': 16.35},
    {'name': 'ACME', 'shares': 75, 'price': 115.65}
]
print(heapq.nlargest(3, list1))
print(heapq.nsmallest(3, list1))
print(heapq.nlargest(2, list2, key=lambda x: x['price']))
print(heapq.nlargest(2, list2, key=lambda x: x['shares']))
"""
迭代工具 - 排列 / 组合 / 笛卡尔积
"""
import itertools

itertools.permutations('ABCD')
itertools.combinations('ABCDE', 3)
itertools.product('ABCD', '123')
collections模块下的工具类

"""
找出序列中出现次数最多的元素
"""
from collections import Counter

words = [
    'look', 'into', 'my', 'eyes', 'look', 'into', 'my', 'eyes',
    'the', 'eyes', 'the', 'eyes', 'the', 'eyes', 'not', 'around',
    'the', 'eyes', "don't", 'look', 'around', 'the', 'eyes',
    'look', 'into', 'my', 'eyes', "you're", 'under'
]
counter = Counter(words)
print(counter.most_common(3))

常用算法:

穷举法 - 又称为暴力破解法,对所有的可能性进行验证,直到找到正确答案。
贪婪法 - 在对问题求解时,总是做出在当前看来是最好的选择,不追求最优解,快速找到满意解。
分治法 - 把一个复杂的问题分成两个或更多的相同或相似的子问题,再把子问题分成更小的子问题,直到可以直接求解的程度,最后将子问题的解进行合并得到原问题的解。
回溯法 - 回溯法又称为试探法,按选优条件向前搜索,当搜索到某一步发现原先选择并不优或达不到目标时,就退回一步重新选择。
动态规划 - 基本思想也是将待求解问题分解成若干个子问题,先求解并保存这些子问题的解,避免产生大量的重复运算。
穷举法例子:百钱百鸡和五人分鱼。

公鸡5元一只 母鸡3元一只 小鸡1元三只
用100元买100只鸡 问公鸡/母鸡/小鸡各多少只

for x in range(20):
    for y in range(33):
        z = 100 - x - y
        if 5 * x + 3 * y + z // 3 == 100 and z % 3 == 0:
            print(x, y, z)

A、B、C、D、E五人在某天夜里合伙捕鱼 最后疲惫不堪各自睡觉
第二天A第一个醒来 他将鱼分为5份 扔掉多余的1条 拿走自己的一份
B第二个醒来 也将鱼分为5份 扔掉多余的1条 拿走自己的一份
然后C、D、E依次醒来也按同样的方式分鱼 问他们至少捕了多少条鱼

fish = 1
while True:
total = fish
enough = True
for _ in range(5):
if (total - 1) % 5 == 0:
total = (total - 1) // 5 * 4
else:
enough = False
break
if enough:
print(fish)
break
fish += 1
贪婪法例子:假设小偷有一个背包,最多能装20公斤赃物,他闯入一户人家,发现如下表所示的物品。很显然,他不能把所有物品都装进背包,所以必须确定拿走哪些物品,留下哪些物品。

名称 价格(美元) 重量(kg)
电脑 200 20
收音机 20 4
钟 175 10
花瓶 50 2
书 10 1
油画 90 9
“”"
贪婪法:在对问题求解时,总是做出在当前看来是最好的选择,不追求最优解,快速找到满意解。

输入:
20 6
电脑 200 20
收音机 20 4
钟 175 10
花瓶 50 2
书 10 1
油画 90 9

"""
class Thing(object):
    """物品"""

    def __init__(self, name, price, weight):
        self.name = name
        self.price = price
        self.weight = weight

    @property
    def value(self):
        """价格重量比"""
        return self.price / self.weight


def input_thing():
    """输入物品信息"""
    name_str, price_str, weight_str = input().split()
    return name_str, int(price_str), int(weight_str)


def main():
    """主函数"""
    max_weight, num_of_things = map(int, input().split())
    all_things = []
    for _ in range(num_of_things):
        all_things.append(Thing(*input_thing()))
    all_things.sort(key=lambda x: x.value, reverse=True)
    total_weight = 0
    total_price = 0
    for thing in all_things:
        if total_weight + thing.weight <= max_weight:
            print(f'小偷拿走了{thing.name}')
            total_weight += thing.weight
            total_price += thing.price
    print(f'总价值: {total_price}美元')


if __name__ == '__main__':
    main()

分治法例子:快速排序。

"""
快速排序 - 选择枢轴对元素进行划分,左边都比枢轴小右边都比枢轴大
"""
def quick_sort(origin_items, comp=lambda x, y: x <= y):
    items = origin_items[:]
    _quick_sort(items, 0, len(items) - 1, comp)
    return items


def _quick_sort(items, start, end, comp):
    if start < end:
        pos = _partition(items, start, end, comp)
        _quick_sort(items, start, pos - 1, comp)
        _quick_sort(items, pos + 1, end, comp)


def _partition(items, start, end, comp):
    pivot = items[end]
    i = start - 1
    for j in range(start, end):
        if comp(items[j], pivot):
            i += 1
            items[i], items[j] = items[j], items[i]
    items[i + 1], items[end] = items[end], items[i + 1]
    return i + 1

回溯法例子:骑士巡逻。

“”"
递归回溯法:叫称为试探法,按选优条件向前搜索,当搜索到某一步,发现原先选择并不优或达不到目标时,就退回一步重新选择,比较经典的问题包括骑士巡逻、八皇后和迷宫寻路等。

"""
import sys
import time

SIZE = 5
total = 0


def print_board(board):
    for row in board:
        for col in row:
            print(str(col).center(4), end='')
        print()


def patrol(board, row, col, step=1):
    if row >= 0 and row < SIZE and \
        col >= 0 and col < SIZE and \
        board[row][col] == 0:
        board[row][col] = step
        if step == SIZE * SIZE:
            global total
            total += 1
            print(f'第{total}种走法: ')
            print_board(board)
        patrol(board, row - 2, col - 1, step + 1)
        patrol(board, row - 1, col - 2, step + 1)
        patrol(board, row + 1, col - 2, step + 1)
        patrol(board, row + 2, col - 1, step + 1)
        patrol(board, row + 2, col + 1, step + 1)
        patrol(board, row + 1, col + 2, step + 1)
        patrol(board, row - 1, col + 2, step + 1)
        patrol(board, row - 2, col + 1, step + 1)
        board[row][col] = 0


def main():
    board = [[0] * SIZE for _ in range(SIZE)]
    patrol(board, SIZE - 1, SIZE - 1)


if __name__ == '__main__':
    main()

动态规划例子1:斐波拉切数列。(不使用动态规划将会是几何级数复杂度)

"""
动态规划 - 适用于有重叠子问题和最优子结构性质的问题
使用动态规划方法所耗时间往往远少于朴素解法(用空间换取时间)
"""
def fib(num, temp={}):
    """用递归计算Fibonacci数"""
    if num in (1, 2):
        return 1
    try:
        return temp[num]
    except KeyError:
        temp[num] = fib(num - 1) + fib(num - 2)
        return temp[num]

动态规划例子2:子列表元素之和的最大值。(使用动态规划可以避免二重循环)

说明:子列表指的是列表中索引(下标)连续的元素构成的列表;列表中的元素是int类型,可能包含正整数、0、负整数;程序输入列表中的元素,输出子列表元素求和的最大值,例如:

输入:1 -2 3 5 -3 2

输出:8

输入:0 -2 3 5 -1 2

输出:9

输入:-9 -2 -3 -5 -3

输出:-2

def main():
    items = list(map(int, input().split()))
    size = len(items)
    overall, partial = {}, {}
    overall[size - 1] = partial[size - 1] = items[size - 1]
    for i in range(size - 2, -1, -1):
        partial[i] = max(items[i], partial[i + 1] + items[i])
        overall[i] = max(partial[i], overall[i + 1])
    print(overall[0])


if __name__ == '__main__':
    main()

函数的使用方式

将函数视为“一等公民”

函数可以赋值给变量
函数可以作为函数的参数
函数可以作为函数的返回值
高阶函数的用法(filter、map以及它们的替代品)

items1 = list(map(lambda x: x ** 2, filter(lambda x: x % 2, range(1, 10))))
items2 = [x ** 2 for x in range(1, 10) if x % 2]

位置参数、可变参数、关键字参数、命名关键字参数

参数的元信息(代码可读性问题)

匿名函数和内联函数的用法(lambda函数)

闭包和作用域问题

Python搜索变量的LEGB顺序(Local --> Embedded --> Global --> Built-in)

global和nonlocal关键字的作用

global:声明或定义全局变量(要么直接使用现有的全局作用域的变量,要么定义一个变量放到全局作用域)。

nonlocal:声明使用嵌套作用域的变量(嵌套作用域必须存在该变量,否则报错)。

装饰器函数(使用装饰器和取消装饰器)

例子:输出函数执行时间的装饰器。

def record_time(func):
    """自定义装饰函数的装饰器"""
    
    @wraps(func)
    def wrapper(*args, **kwargs):
        start = time()
        result = func(*args, **kwargs)
        print(f'{func.__name__}: {time() - start}秒')
        return result
        
    return wrapper

如果装饰器不希望跟print函数耦合,可以编写带参数的装饰器。

from functools import wraps
from time import time


def record(output):
    """自定义带参数的装饰器"""
	
	def decorate(func):
		
		@wraps(func)
		def wrapper(*args, **kwargs):
			start = time()
			result = func(*args, **kwargs)
			output(func.__name__, time() - start)
			return result
            
		return wrapper
	
	return decorate
from functools import wraps
from time import time


class Record():
    """自定义装饰器类(通过__call__魔术方法使得对象可以当成函数调用)"""
def __init__(self, output):
    self.output = output

def __call__(self, func):

    @wraps(func)
    def wrapper(*args, **kwargs):
        start = time()
        result = func(*args, **kwargs)
        self.output(func.__name__, time() - start)
        return result

    return wrapper

说明:由于对带装饰功能的函数添加了@wraps装饰器,可以通过func.__wrapped__方式获得被装饰之前的函数或类来取消装饰器的作用。

例子:用装饰器来实现单例模式。

from functools import wraps


def singleton(cls):
    """装饰类的装饰器"""
    instances = {}

@wraps(cls)
def wrapper(*args, **kwargs):
    if cls not in instances:
        instances[cls] = cls(*args, **kwargs)
    return instances[cls]

return wrapper

@singleton class President():
“”“总统(单例类)”""
pass

说明:上面的代码中用到了闭包(closure),不知道你是否已经意识到了。还没有一个小问题就是,上面的代码并没有实现线程安全的单例,如果要实现线程安全的单例应该怎么做呢?

from functools import wraps


def singleton(cls):
    """线程安全的单例装饰器"""
    instances = {}
    locker = Lock()

    @wraps(cls)
    def wrapper(*args, **kwargs):
        if cls not in instances:
            with locker:
                if cls not in instances:
                    instances[cls] = cls(*args, **kwargs)
        return instances[cls]

    return wrapper
面向对象相关知识

三大支柱:封装、继承、多态

例子:工资结算系统。

"""
月薪结算系统 - 部门经理每月15000 程序员每小时200 销售员1800底薪加销售额5%提成
"""
from abc import ABCMeta, abstractmethod


class Employee(metaclass=ABCMeta):
    """员工(抽象类)"""

    def __init__(self, name):
        self.name = name

    @abstractmethod
    def get_salary(self):
        """结算月薪(抽象方法)"""
        pass


class Manager(Employee):
    """部门经理"""

    def get_salary(self):
        return 15000.0


class Programmer(Employee):
    """程序员"""

    def __init__(self, name, working_hour=0):
        self.working_hour = working_hour
        super().__init__(name)

    def get_salary(self):
        return 200.0 * self.working_hour


class Salesman(Employee):
    """销售员"""

    def __init__(self, name, sales=0.0):
        self.sales = sales
        super().__init__(name)

    def get_salary(self):
        return 1800.0 + self.sales * 0.05


class EmployeeFactory():
    """创建员工的工厂(工厂模式 - 通过工厂实现对象使用者和对象之间的解耦合)"""

    @staticmethod
    def create(emp_type, *args, **kwargs):
        """创建员工"""
        emp_type = emp_type.upper()
        emp = None
        if emp_type == 'M':
            emp = Manager(*args, **kwargs)
        elif emp_type == 'P':
            emp = Programmer(*args, **kwargs)
        elif emp_type == 'S':
            emp = Salesman(*args, **kwargs)
        return emp


def main():
    """主函数"""
    emps = [
        EmployeeFactory.create('M', '曹操'), 
        EmployeeFactory.create('P', '荀彧', 120),
        EmployeeFactory.create('P', '郭嘉', 85), 
        EmployeeFactory.create('S', '典韦', 123000),
    ]
    for emp in emps:
        print('%s: %.2f元' % (emp.name, emp.get_salary()))


if __name__ == '__main__':
    main()
类与类之间的关系

is-a关系:继承
has-a关系:关联 / 聚合 / 合成
use-a关系:依赖
例子:扑克游戏。

"""
经验:符号常量总是优于字面常量,枚举类型是定义符号常量的最佳选择
"""
from enum import Enum, unique

import random


@unique
class Suite(Enum):
    """花色"""

    SPADE, HEART, CLUB, DIAMOND = range(4)

    def __lt__(self, other):
        return self.value < other.value


class Card():
    """牌"""

    def __init__(self, suite, face):
        """初始化方法"""
        self.suite = suite
        self.face = face

    def show(self):
        """显示牌面"""
        suites = ['♠️', '♥️', '♣️', '♦️']
        faces = ['', 'A', '2', '3', '4', '5', '6', '7', '8', '9', '10', 'J', 'Q', 'K']
        return f'{suites[self.suite.value]} {faces[self.face]}'

    def __str__(self):
        return self.show()

    def __repr__(self):
        return self.show()


class Poker():
    """扑克"""

    def __init__(self):
        self.index = 0
        self.cards = [Card(suite, face)
                      for suite in Suite
                      for face in range(1, 14)]

    def shuffle(self):
        """洗牌(随机乱序)"""
        random.shuffle(self.cards)
        self.index = 0

    def deal(self):
        """发牌"""
        card = self.cards[self.index]
        self.index += 1
        return card

    @property
    def has_more(self):
        return self.index < len(self.cards)


class Player():
    """玩家"""

    def __init__(self, name):
        self.name = name
        self.cards = []

    def get_one(self, card):
        """摸一张牌"""
        self.cards.append(card)

    def sort(self, comp=lambda card: (card.suite, card.face)):
        """整理手上的牌"""
        self.cards.sort(key=comp)


def main():
    """主函数"""
    poker = Poker()
    poker.shuffle()
    players = [Player('东邪'), Player('西毒'), Player('南帝'), Player('北丐')]
    while poker.has_more:
        for player in players:
                player.get_one(poker.deal())
    for player in players:
        player.sort()
        print(player.name, end=': ')
        print(player.cards)


if __name__ == '__main__':
    main()

对象的复制(深复制/深拷贝/深度克隆和浅复制/浅拷贝/影子克隆)

垃圾回收、循环引用和弱引用

Python使用了自动化内存管理,这种管理机制以引用计数为基础,同时也引入了标记-清除和分代收集两种机制为辅的策略。

typedef struct_object {
    /* 引用计数 */
    int ob_refcnt;
    /* 对象指针 */
    struct_typeobject *ob_type;
} PyObject;
/* 增加引用计数的宏定义 */
#define Py_INCREF(op)   ((op)->ob_refcnt++)
/* 减少引用计数的宏定义 */
#define Py_DECREF(op) \ //减少计数
    if (--(op)->ob_refcnt != 0) \
        ; \
    else \
        __Py_Dealloc((PyObject *)(op))

导致引用计数+1的情况:

对象被创建,例如a = 23
对象被引用,例如b = a
对象被作为参数,传入到一个函数中,例如f(a)
对象作为一个元素,存储在容器中,例如list1 = [a, a]
导致引用计数-1的情况:

对象的别名被显式销毁,例如del a
对象的别名被赋予新的对象,例如a = 24
一个对象离开它的作用域,例如f函数执行完毕时,f函数中的局部变量(全局变量不会)
对象所在的容器被销毁,或从容器中删除对象
引用计数可能会导致循环引用问题,而循环引用会导致内存泄露,如下面的代码所示。为了解决这个问题,Python中引入了“标记-清除”和“分代收集”。在创建一个对象的时候,对象被放在第一代中,如果在第一代的垃圾检查中对象存活了下来,该对象就会被放到第二代中,同理在第二代的垃圾检查中对象存活下来,该对象就会被放到第三代中。

#循环引用会导致内存泄露 - Python除了引用技术还引入了标记清理和分代回收
#在Python 3.6以前如果重写__del__魔术方法会导致循环引用处理失效
#如果不想造成循环引用可以使用弱引用
list1 = []
list2 = []
list1.append(list2)
list2.append(list1)
以下情况会导致垃圾回收:

调用gc.collect()
gc模块的计数器达到阀值

程序退出
如果循环引用中两个对象都定义了__del__方法,gc模块不会销毁这些不可达对象,因为gc模块不知道应该先调用哪个对象的__del__方法,这个问题在Python 3.6中得到了解决。

也可以通过weakref模块构造弱引用的方式来解决循环引用的问题。

魔法属性和方法(请参考《Python魔法方法指南》)

有几个小问题请大家思考:

自定义的对象能不能使用运算符做运算?
自定义的对象能不能放到set中?能去重吗?
自定义的对象能不能作为dict的键?
自定义的对象能不能使用上下文语法?
混入(Mixin)

**例子:**自定义字典限制只有在指定的key不存在时才能在字典中设置键值对。

class SetOnceMappingMixin():
    """自定义混入类"""
    __slots__ = ()

    def __setitem__(self, key, value):
        if key in self:
            raise KeyError(str(key) + ' already set')
        return super().__setitem__(key, value)


class SetOnceDict(SetOnceMappingMixin, dict):
    """自定义字典"""
    pass


my_dict= SetOnceDict()
try:
    my_dict['username'] = 'jackfrued'
    my_dict['username'] = 'hellokitty'
except KeyError:
    pass
print(my_dict)

元编程和元类

例子:用元类实现单例模式。

import threading


class SingletonMeta(type):
    """自定义元类"""

def __init__(cls, *args, **kwargs):
    cls.__instance = None
    cls.__lock = threading.Lock()
    super().__init__(*args, **kwargs)

def __call__(cls, *args, **kwargs):
    if cls.__instance is None:
        with cls.__lock:
            if cls.__instance is None:
                cls.__instance = super().__call__(*args, **kwargs)
    return cls.__instance


class President(metaclass=SingletonMeta):
    """总统(单例类)"""
    pass

面向对象设计原则

单一职责原则 (SRP)- 一个类只做该做的事情(类的设计要高内聚)
开闭原则 (OCP)- 软件实体应该对扩展开发对修改关闭
依赖倒转原则(DIP)- 面向抽象编程(在弱类型语言中已经被弱化)
里氏替换原则(LSP) - 任何时候可以用子类对象替换掉父类对象
接口隔离原则(ISP)- 接口要小而专不要大而全(Python中没有接口的概念)
合成聚合复用原则(CARP) - 优先使用强关联关系而不是继承关系复用代码
最少知识原则(迪米特法则,LoD)- 不要给没有必然联系的对象发消息
说明:上面加粗的字母放在一起称为面向对象的SOLID原则。

GoF设计模式

创建型模式:单例、工厂、建造者、原型
结构型模式:适配器、门面(外观)、代理
行为型模式:迭代器、观察者、状态、策略
例子:可插拔的哈希算法。

class StreamHasher():
    """哈希摘要生成器(策略模式)"""

    def __init__(self, alg='md5', size=4096):
        self.size = size
        alg = alg.lower()
        self.hasher = getattr(__import__('hashlib'), alg.lower())()

    def __call__(self, stream):
        return self.to_digest(stream)

    def to_digest(self, stream):
        """生成十六进制形式的摘要"""
        for buf in iter(lambda: stream.read(self.size), b''):
            self.hasher.update(buf)
        return self.hasher.hexdigest()

def main():
    """主函数"""
    hasher1 = StreamHasher()
    with open('Python-3.7.1.tgz', 'rb') as stream:
        print(hasher1.to_digest(stream))
    hasher2 = StreamHasher('sha1')
    with open('Python-3.7.1.tgz', 'rb') as stream:
        print(hasher2(stream))


if __name__ == '__main__':
    main()
迭代器和生成器

和迭代器相关的魔术方法(__iter__和__next__)

两种创建生成器的方式(生成器表达式和yield关键字)

def fib(num):
    """生成器"""
    a, b = 0, 1
    for _ in range(num):
        a, b = b, a + b
        yield a
   
   
class Fib(object):
    """迭代器"""

def __init__(self, num):
    self.num = num
    self.a, self.b = 0, 1
    self.idx = 0

def __iter__(self):
    return self

def __next__(self):
    if self.idx < self.num:
        self.a, self.b = self.b, self.a + self.b
        self.idx += 1
        return self.a
    raise StopIteration()

并发编程

Python中实现并发编程的三种方案:多线程、多进程和异步I/O。并发编程的好处在于可以提升程序的执行效率以及改善用户体验;坏处在于并发的程序不容易开发和调试,同时对其他程序来说它并不友好。

多线程:Python中提供了Thread类并辅以Lock、Condition、Event、Semaphore和Barrier。Python中有GIL来防止多个线程同时执行本地字节码,这个锁对于CPython是必须的,因为CPython的内存管理并不是线程安全的,因为GIL的存在多线程并不能发挥CPU的多核特性。

“”"
面试题:进程和线程的区别和联系?
进程 - 操作系统分配内存的基本单位 - 一个进程可以包含一个或多个线程
线程 - 操作系统分配CPU的基本单位
并发编程(concurrent programming)

  1. 提升执行性能 - 让程序中没有因果关系的部分可以并发的执行

  2. 改善用户体验 - 让耗时间的操作不会造成程序的假死

    “”"
    import glob
    import os
    import threading

    from PIL import Image

    PREFIX = ‘thumbnails’

    def generate_thumbnail(infile, size, format=‘PNG’):
    “”“生成指定图片文件的缩略图”""
    file, ext = os.path.splitext(infile)
    file = file[file.rfind(’/’) + 1:]
    outfile = f’{PREFIX}/{file}{size[0]}{size[1]}.{ext}’
    img = Image.open(infile)
    img.thumbnail(size, Image.ANTIALIAS)
    img.save(outfile, format)

    def main():
    “”“主函数”""
    if not os.path.exists(PREFIX):
    os.mkdir(PREFIX)
    for infile in glob.glob(‘images/*.png’):
    for size in (32, 64, 128):
    # 创建并启动线程
    threading.Thread(
    target=generate_thumbnail,
    args=(infile, (size, size))
    ).start()

    if name == ‘main’:
    main()
    多个线程竞争资源的情况

    “”"

多线程程序如果没有竞争资源处理起来通常也比较简单
当多个线程竞争临界资源的时候如果缺乏必要的保护措施就会导致数据错乱
说明:临界资源就是被多个线程竞争的资源

"""
import time
import threading

from concurrent.futures import ThreadPoolExecutor


class Account(object):
    """银行账户"""

    def __init__(self):
        self.balance = 0.0
        self.lock = threading.Lock()

    def deposit(self, money):
        # 通过锁保护临界资源
        with self.lock:
            new_balance = self.balance + money
            time.sleep(0.001)
            self.balance = new_balance


class AddMoneyThread(threading.Thread):
    """自定义线程类"""

    def __init__(self, account, money):
        self.account = account
        self.money = money
        # 自定义线程的初始化方法中必须调用父类的初始化方法
        super().__init__()

    def run(self):
        # 线程启动之后要执行的操作
        self.account.deposit(self.money)

def main():
    """主函数"""
    account = Account()
    # 创建线程池
    pool = ThreadPoolExecutor(max_workers=10)
    futures = []
    for _ in range(100):
        # 创建线程的第1种方式
        # threading.Thread(
        #     target=account.deposit, args=(1, )
        # ).start()
        # 创建线程的第2种方式
        # AddMoneyThread(account, 1).start()
        # 创建线程的第3种方式
        # 调用线程池中的线程来执行特定的任务
        future = pool.submit(account.deposit, 1)
        futures.append(future)
    # 关闭线程池
    pool.shutdown()
    for future in futures:
        future.result()
    print(account.balance)


if __name__ == '__main__':
    main()

修改上面的程序,启动5个线程向账户中存钱,5个线程从账户中取钱,取钱时如果余额不足就暂停线程进行等待。为了达到上述目标,需要对存钱和取钱的线程进行调度,在余额不足时取钱的线程暂停并释放锁,而存钱的线程将钱存入后要通知取钱的线程,使其从暂停状态被唤醒。可以使用threading模块的Condition来实现线程调度,该对象也是基于锁来创建的,代码如下所示:

"""
多个线程竞争一个资源 - 保护临界资源 - 锁(Lock/RLock)
多个线程竞争多个资源(线程数>资源数) - 信号量(Semaphore)
多个线程的调度 - 暂停线程执行/唤醒等待中的线程 - Condition
"""
from concurrent.futures import ThreadPoolExecutor
from random import randint
from time import sleep

import threading


class Account():
    """银行账户"""

    def __init__(self, balance=0):
        self.balance = balance
        lock = threading.Lock()
        self.condition = threading.Condition(lock)

    def withdraw(self, money):
        """取钱"""
        with self.condition:
            while money > self.balance:
                self.condition.wait()
            new_balance = self.balance - money
            sleep(0.001)
            self.balance = new_balance

    def deposit(self, money):
        """存钱"""
        with self.condition:
            new_balance = self.balance + money
            sleep(0.001)
            self.balance = new_balance
            self.condition.notify_all()


def add_money(account):
    while True:
        money = randint(5, 10)
        account.deposit(money)
        print(threading.current_thread().name, 
              ':', money, '====>', account.balance)
        sleep(0.5)


def sub_money(account):
    while True:
        money = randint(10, 30)
        account.withdraw(money)
        print(threading.current_thread().name, 
              ':', money, '<====', account.balance)
        sleep(1)


def main():
    account = Account()
    with ThreadPoolExecutor(max_workers=10) as pool:
        for _ in range(5):
            pool.submit(add_money, account)
            pool.submit(sub_money, account)


if __name__ == '__main__':
    main()

多进程:多进程可以有效的解决GIL的问题,实现多进程主要的类是Process,其他辅助的类跟threading模块中的类似,进程间共享数据可以使用管道、套接字等,在multiprocessing模块中有一个Queue类,它基于管道和锁机制提供了多个进程共享的队列。下面是官方文档上关于多进程和进程池的一个示例。

"""
多进程和进程池的使用
多线程因为GIL的存在不能够发挥CPU的多核特性
对于计算密集型任务应该考虑使用多进程
time python3 example22.py
real    0m11.512s
user    0m39.319s
sys     0m0.169s
使用多进程后实际执行时间为11.512秒,而用户时间39.319秒约为实际执行时间的4倍
这就证明我们的程序通过多进程使用了CPU的多核特性,而且这台计算机配置了4核的CPU
"""
import concurrent.futures
import math

PRIMES = [
    1116281,
    1297337,
    104395303,
    472882027,
    533000389,
    817504243,
    982451653,
    112272535095293,
    112582705942171,
    112272535095293,
    115280095190773,
    115797848077099,
    1099726899285419
] * 5


def is_prime(n):
    """判断素数"""
    if n % 2 == 0:
        return False

    sqrt_n = int(math.floor(math.sqrt(n)))
    for i in range(3, sqrt_n + 1, 2):
        if n % i == 0:
            return False
    return True


def main():
    """主函数"""
    with concurrent.futures.ProcessPoolExecutor() as executor:
        for number, prime in zip(PRIMES, executor.map(is_prime, PRIMES)):
            print('%d is prime: %s' % (number, prime))


if __name__ == '__main__':
    main()

说明:多线程和多进程的比较。

以下情况需要使用多线程:

程序需要维护许多共享的状态(尤其是可变状态),Python中的列表、字典、集合都是线程安全的,所以使用线程而不是进程维护共享状态的代价相对较小。
程序会花费大量时间在I/O操作上,没有太多并行计算的需求且不需占用太多的内存。
以下情况需要使用多进程:

程序执行计算密集型任务(如:字节码操作、数据处理、科学计算)。
程序的输入可以并行的分成块,并且可以将运算结果合并。
程序在内存使用方面没有任何限制且不强依赖于I/O操作(如:读写文件、套接字等)。
异步处理:从调度程序的任务队列中挑选任务,该调度程序以交叉的形式执行这些任务,我们并不能保证任务将以某种顺序去执行,因为执行顺序取决于队列中的一项任务是否愿意将CPU处理时间让位给另一项任务。异步任务通常通过多任务协作处理的方式来实现,由于执行时间和顺序的不确定,因此需要通过回调式编程或者future对象来获取任务执行的结果。Python 3通过asyncio模块和await和async关键字(在Python 3.7中正式被列为关键字)来支持异步处理。

"""
异步I/O - async / await
"""
import asyncio


def num_generator(m, n):
    """指定范围的数字生成器"""
    yield from range(m, n + 1)


async def prime_filter(m, n):
    """素数过滤器"""
    primes = []
    for i in num_generator(m, n):
        flag = True
        for j in range(2, int(i ** 0.5 + 1)):
            if i % j == 0:
                flag = False
                break
        if flag:
            print('Prime =>', i)
            primes.append(i)

        await asyncio.sleep(0.001)
    return tuple(primes)


async def square_mapper(m, n):
    """平方映射器"""
    squares = []
    for i in num_generator(m, n):
        print('Square =>', i * i)
        squares.append(i * i)

        await asyncio.sleep(0.001)
    return squares


def main():
    """主函数"""
    loop = asyncio.get_event_loop()
    future = asyncio.gather(prime_filter(2, 100), square_mapper(1, 100))
    future.add_done_callback(lambda x: print(x.result()))
    loop.run_until_complete(future)
    loop.close()


if __name__ == '__main__':
    main()

说明:上面的代码使用get_event_loop函数获得系统默认的事件循环,通过gather函数可以获得一个future对象,future对象的add_done_callback可以添加执行完成时的回调函数,loop对象的run_until_complete方法可以等待通过future对象获得协程执行结果。

Python中有一个名为aiohttp的三方库,它提供了异步的HTTP客户端和服务器,这个三方库可以跟asyncio模块一起工作,并提供了对Future对象的支持。Python 3.6中引入了async和await来定义异步执行的函数以及创建异步上下文,在Python 3.7中它们正式成为了关键字。下面的代码异步的从5个URL中获取页面并通过正则表达式的命名捕获组提取了网站的标题。

import asyncio
import re

import aiohttp

PATTERN = re.compile(r'\(?P.*)\<\/title\>')


async def fetch_page(session, url):
    async with session.get(url, ssl=False) as resp:
        return await resp.text()


async def show_title(url):
    async with aiohttp.ClientSession() as session:
        html = await fetch_page(session, url)
        print(PATTERN.search(html).group('title'))


def main():
    urls = ('https://www.python.org/',
            'https://git-scm.com/',
            'https://www.jd.com/',
            'https://www.taobao.com/',
            'https://www.douban.com/')
    loop = asyncio.get_event_loop()
    tasks = [show_title(url) for url in urls]
    loop.run_until_complete(asyncio.wait(tasks))
    loop.close()


if __name__ == '__main__':
    main()
</code></pre> 
  <p>说明:异步I/O与多进程的比较。</p> 
  <p>当程序不需要真正的并发性或并行性,而是更多的依赖于异步处理和回调时,asyncio就是一种很好的选择。如果程序中有大量的等待与休眠时,也应该考虑asyncio,它很适合编写没有实时数据处理需求的Web应用服务器。</p> 
  <p>Python还有很多用于处理并行任务的三方库,例如:joblib、PyMP等。实际开发中,要提升系统的可扩展性和并发性通常有垂直扩展(增加单个节点的处理能力)和水平扩展(将单个节点变成多个节点)两种做法。可以通过消息队列来实现应用程序的解耦合,消息队列相当于是多线程同步队列的扩展版本,不同机器上的应用程序相当于就是线程,而共享的分布式消息队列就是原来程序中的Queue。消息队列(面向消息的中间件)的最流行和最标准化的实现是AMQP(高级消息队列协议),AMQP源于金融行业,提供了排队、路由、可靠传输、安全等功能,最著名的实现包括:Apache的ActiveMQ、RabbitMQ等。</p> 
  <p>要实现任务的异步化,可以使用名为Celery的三方库。Celery是Python编写的分布式任务队列,它使用分布式消息进行工作,可以基于RabbitMQ或Redis来作为后端的消息代理。</p> 
 </div> 
</div>
                            </div>
                        </div>
                    </div>
                    <!--PC和WAP自适应版-->
                    <div id="SOHUCS" sid="1305400467840339968"></div>
                    <script type="text/javascript" src="/views/front/js/chanyan.js"></script>
                    <!-- 文章页-底部 动态广告位 -->
                    <div class="youdao-fixed-ad" id="detail_ad_bottom"></div>
                </div>
                <div class="col-md-3">
                    <div class="row" id="ad">
                        <!-- 文章页-右侧1 动态广告位 -->
                        <div id="right-1" class="col-lg-12 col-md-12 col-sm-4 col-xs-4 ad">
                            <div class="youdao-fixed-ad" id="detail_ad_1"> </div>
                        </div>
                        <!-- 文章页-右侧2 动态广告位 -->
                        <div id="right-2" class="col-lg-12 col-md-12 col-sm-4 col-xs-4 ad">
                            <div class="youdao-fixed-ad" id="detail_ad_2"></div>
                        </div>
                        <!-- 文章页-右侧3 动态广告位 -->
                        <div id="right-3" class="col-lg-12 col-md-12 col-sm-4 col-xs-4 ad">
                            <div class="youdao-fixed-ad" id="detail_ad_3"></div>
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>
    <div class="container">
        <h4 class="pt20 mb15 mt0 border-top">你可能感兴趣的:(Python,100,Days,Python入门教程100天)</h4>
        <div id="paradigm-article-related">
            <div class="recommend-post mb30">
                <ul class="widget-links">
                    <li><a href="/article/1950233451282100224.htm"
                           title="python 读excel每行替换_Python脚本操作Excel实现批量替换功能" target="_blank">python 读excel每行替换_Python脚本操作Excel实现批量替换功能</a>
                        <span class="text-muted">weixin_39646695</span>
<a class="tag" taget="_blank" href="/search/python/1.htm">python</a><a class="tag" taget="_blank" href="/search/%E8%AF%BBexcel%E6%AF%8F%E8%A1%8C%E6%9B%BF%E6%8D%A2/1.htm">读excel每行替换</a>
                        <div>Python脚本操作Excel实现批量替换功能大家好,给大家分享下如何使用Python脚本操作Excel实现批量替换。使用的工具Openpyxl,一个处理excel的python库,处理excel,其实针对的就是WorkBook,Sheet,Cell这三个最根本的元素~明确需求原始excel如下我们的目标是把下面excel工作表的sheet1表页A列的内容“替换我吧”批量替换为B列的“我用来替换的</div>
                    </li>
                    <li><a href="/article/1950233199242178560.htm"
                           title="x86-64汇编语言训练程序与实战" target="_blank">x86-64汇编语言训练程序与实战</a>
                        <span class="text-muted">十除以十等于一</span>

                        <div>本文还有配套的精品资源,点击获取简介:汇编语言是一种低级语言,与机器代码紧密相关,特别适用于编写系统级代码及性能要求高的应用。nasm编译器是针对x86和x86-64架构的汇编语言编译器,支持多种语法风格和指令集。项目Euler提供数学和计算机科学问题,鼓励编程技巧应用,前100个问题的答案可共享。x86-64架构扩展了寄存器数量并引入新指令,提升了数据处理效率。学习汇编语言能够深入理解计算机底层</div>
                    </li>
                    <li><a href="/article/1950232783670538240.htm"
                           title="自律打卡第四天:比昨天进步一点点" target="_blank">自律打卡第四天:比昨天进步一点点</a>
                        <span class="text-muted">花儿的念想</span>

                        <div>今天新闻我们县城又确诊了一例,截止目前已经确诊的三例了,打开,看了一篇简友写的武汉的真实情况,有病住不了院,还没等到床位已经去世的消息,心里更加的难受,武汉尚且这样,如果是我们这没有高速没有火车的十八线的小县城发生这种情况,那情况将是更加的不堪设想,不敢想,唯有祈求灾难早点快去,平安才是最大的福气。突然觉得我的自律打卡,比昨天进步一点点。更希望疫情战争每一天都要比昨天好一点,希望一觉醒来听到的是好</div>
                    </li>
                    <li><a href="/article/1950231308781285376.htm"
                           title="力扣热题100-------54. 螺旋矩阵" target="_blank">力扣热题100-------54. 螺旋矩阵</a>
                        <span class="text-muted">海航Java之路</span>
<a class="tag" taget="_blank" href="/search/%E5%8A%9B%E6%89%A3/1.htm">力扣</a><a class="tag" taget="_blank" href="/search/leetcode/1.htm">leetcode</a><a class="tag" taget="_blank" href="/search/%E7%9F%A9%E9%98%B5/1.htm">矩阵</a><a class="tag" taget="_blank" href="/search/java/1.htm">java</a>
                        <div>给你一个m行n列的矩阵matrix,请按照顺时针螺旋顺序,返回矩阵中的所有元素。示例1:输入:matrix=[[1,2,3],[4,5,6],[7,8,9]]输出:[1,2,3,6,9,8,7,4,5]示例2:输入:matrix=[[1,2,3,4],[5,6,7,8],[9,10,11,12]]输出:[1,2,3,4,8,12,11,10,9,5,6,7]提示:m==matrix.lengthn</div>
                    </li>
                    <li><a href="/article/1950231254427299840.htm"
                           title="我不懂什么是爱,但我给你全部我拥有的" target="_blank">我不懂什么是爱,但我给你全部我拥有的</a>
                        <span class="text-muted">香尧</span>

                        <div>因为怕黑,所以愿意陪伴在夜中行走的人,给他一点点的安全感。因为渴望温柔与爱,所以愿意为别的孩子付出爱与温柔。因为曾遭受侮辱和伤害,所以不以同样的方式施于其他人。如果你向别人出之以利刃,对方还了你爱与包容,真的不要感激他,真的不要赞美他。每一个被人伤害过的人心里都留下了一颗仇恨的种子,他也会想要有一天以眼还眼,以牙还牙。但他未让那颗种子生根发芽,他用一把心剑又一次刺向他自己,用他血荐仇恨,开出一朵温</div>
                    </li>
                    <li><a href="/article/1950230873060208640.htm"
                           title="你要记住,最重要的是:随时做好准备,为了你可能成为更好的自己,放弃现在的自己。" target="_blank">你要记住,最重要的是:随时做好准备,为了你可能成为更好的自己,放弃现在的自己。</a>
                        <span class="text-muted">霖霖z</span>

                        <div>打卡人:周云日期:2018年11月09日【日精进打卡第180天】【知~学习】《六项精进》0遍共214遍《通篇》1遍共106遍《大学》2遍共347遍《坚强工作,温柔生活》ok《不抱怨的世界》104-108页《经典名句》你要记住,最重要的是:随时做好准备,为了你可能成为更好的自己,放弃现在的自己。【行~实践】一、修身:(对自己个人)1、坚持打卡二、齐家:(对家庭和家人)打扫卫生,接送孩子,洗衣做饭,陪</div>
                    </li>
                    <li><a href="/article/1950228596207448064.htm"
                           title="日更50天有什么收益?" target="_blank">日更50天有什么收益?</a>
                        <span class="text-muted">星湾二宝</span>

                        <div>坚持在平台上日更50天了,平台也为我生成了日更50天徽章,小开心一下这份坚持。日更50天徽章那坚持50天都有哪些收益呢?收益一,就是最直观的那些钻和贝,我这边确实不太高,但是这些贝足够支撑我保持会员的资格,能够在发文的时候帮助友友们去除广告,方便阅读。钻和贝收益二,文章的收获,日更50天,坚持写作3.7万文字,书写的文字也从开始的流水账/碎碎念逐渐加入自己的思考和观点。以前,一个念头会一晃而过,如</div>
                    </li>
                    <li><a href="/article/1950228158863175680.htm"
                           title="英伟达靠什么支撑起了4万亿?AI泡沫还能撑多久?" target="_blank">英伟达靠什么支撑起了4万亿?AI泡沫还能撑多久?</a>
                        <span class="text-muted"></span>

                        <div>英伟达市值突破4万亿美元,既是AI算力需求爆发的直接体现,也暗含市场对未来的狂热预期。其支撑逻辑与潜在风险并存,而AI泡沫的可持续性则取决于技术、商业与地缘政治的复杂博弈。⚙️一、英伟达4万亿市值的核心支撑因素技术垄断与生态壁垒硬件优势:英伟达GPU在AI训练市场占有率超87%,H100芯片的FP16算力达1979TFLOPS,领先竞品3-5倍。CUDA生态:400万开发者构建的软件护城河,成为A</div>
                    </li>
                    <li><a href="/article/1950226550444060672.htm"
                           title="中原焦点团队吴瑕瑜焦点解决初级第18期坚持分享第695天 2021年12月6号" target="_blank">中原焦点团队吴瑕瑜焦点解决初级第18期坚持分享第695天 2021年12月6号</a>
                        <span class="text-muted">卿安</span>

                        <div>中原焦点团队吴瑕瑜焦点解决初级第18期坚持分享第695天2021年12月6号相信相信的力量。很多时候我们忽视了相信的力量,当看到孩子遇到困难、挫折,或者可能犯错时,我们急于去帮忙,这至少部分暗含不相信孩子有能力自己解决,“等不及”,少了对孩子有权决定是否需要帮忙的尊重,缺乏界限,容易引起冲突,并影响孩子的独立能力。对孩子的成长,很多时候,家长的相信比具体帮助更重要。</div>
                    </li>
                    <li><a href="/article/1950223879330918400.htm"
                           title="第八章 竟然是他" target="_blank">第八章 竟然是他</a>
                        <span class="text-muted">橥橥</span>

                        <div>十天之后,京城已在眼前。沐子莹总算松了口,天子脚下,相对安全。马车在城门外停下,杨嬷嬷掀了帘子往外望去,哀叹了一声。沐子莹拍拍身上的灰尘安慰她说:“嬷嬷,别怕,马上就要到府了,咱们可得把那车夫的事跟主母讲一讲,让主她这个当家的给我们作主才是。”嬷嬷却连连摆手,“不可啊小姐,咱们能平安回府就是幸事,车夫的事……就说他摔死在半路,其它的,莫要再提了吧。”“若真是车夫生事那算是万幸了,只怕容不得我们的,</div>
                    </li>
                    <li><a href="/article/1950222858454102016.htm"
                           title="《路远连着天》 第二 章 在 路 上 7" target="_blank">《路远连着天》 第二 章 在 路 上 7</a>
                        <span class="text-muted">亚宁</span>

                        <div>大路镇的街道两旁尽是店铺,气派者是红门柱子雕花门窗,一般则多为布匹小百货店,还有几家门面朝外的车马大店,和一家颇有气势的典当铺。街上来往人还真不少,有挑担叫卖水果的,有背篓子路过的,还有衣冠楚楚,悠哉悠哉,甩着双手散步的有钱爷。耿六想着先寻姑妈家,还是先到兵营看那几个土匪呢?也只是一转念,他选择了后者,跟在几个闲人后,就来到了在镇外山头上曾看到过的那处飘着晴天白日旗的兵营门外。这里,围观的人乱哄哄</div>
                    </li>
                    <li><a href="/article/1950221461255942144.htm"
                           title="你对待万事万物的态度" target="_blank">你对待万事万物的态度</a>
                        <span class="text-muted">行靜</span>

                        <div>昨晚爸爸把洒水壶灌满水,对我说:你也该去浇浇你阳台上的花咯。这么大的天气,几天没浇水都快死了。我才意识到自己容易突然间忽视一些事情。尤其是身旁的一些事,可能它们呆久了,反而习以为常。想想每天的生活状态就是在不断的重复着一些事,有点固定模式。没有什么特别发生。记录我的一天:上班,挤公交,用手机或电脑,吃饭,上课。没有</div>
                    </li>
                    <li><a href="/article/1950220311752404992.htm"
                           title="为他找了一百个理由" target="_blank">为他找了一百个理由</a>
                        <span class="text-muted">顾安安呐</span>

                        <div>我曾经试图从蛛丝马迹里找出理由,去告诉自己你很爱我。相信很多恋爱过的人都有这种经历:他爱我吗?朋友小邹是大家公认的那种乐观开朗的女孩。前一段时间却钻起了牛角尖,她开始变得敏感多疑,而这些与她之前的性格完全判若两人。她现男友得不到我们的认可,但是她爱他,总是从蛛丝马迹里找证据。他一天不回他消息,她就告诉自己他在忙;他和别的女生有说有笑,她问他,只要他说是同学让她不要发神经,她就愿意傻傻的相信他;他对</div>
                    </li>
                    <li><a href="/article/1950219953118441472.htm"
                           title="编程算法:技术创新的引擎与业务增长的核心驱动力" target="_blank">编程算法:技术创新的引擎与业务增长的核心驱动力</a>
                        <span class="text-muted"></span>

                        <div>在数字经济时代,算法已成为推动技术创新与业务增长的隐形引擎。从存内计算突破冯·诺依曼瓶颈,到动态规划优化万亿级金融交易,编程算法正在重塑产业竞争格局。一、存内计算:突破冯·诺依曼瓶颈的算法革命1.1存内计算的基本原理传统计算架构中90%的能耗消耗在数据搬运上。存内计算(Processing-in-Memory)通过直接在存储单元执行计算,实现能效10-100倍提升:#传统计算vs存内计算能耗模型i</div>
                    </li>
                    <li><a href="/article/1950219796981280768.htm"
                           title="冯玙哲诗歌。你的微笑。" target="_blank">冯玙哲诗歌。你的微笑。</a>
                        <span class="text-muted">冯玙哲</span>

                        <div>图片发自App黑夜的河流流过我的臂弯静谧的爱情无声无息的穿行关于一首诗的故事,没有苍凉说好的相聚,总会有日子分分离离总要团圆谁在你的玻璃上写下名字诗句上泛滥着生与死长久的相依依靠着你的承诺,才站立着望见远方火热的太阳,优雅的月亮明媚的笑靥背后藏匿的悲伤总让人疼痛一天过去,寺庙的钟声没有响起一束束鲜花灿烂,姑娘的背囊里有猫古老的瓷器,破烂的木头,多肉花盆不经意的就触碰了爱人的眼泪于是我匍匐在路上,夜</div>
                    </li>
                    <li><a href="/article/1950219036667211776.htm"
                           title="你好,2020年" target="_blank">你好,2020年</a>
                        <span class="text-muted">瑄瑄妍妍的妈咪</span>

                        <div>早上好,今天是2020年的第一天,也就是元旦,新年新的一天开始了。新的开始,重新规划未来的一年。从今天开始,用了一个新的记账软件,之前的随手记软件,也没有删除,只是重新下载了一个别的软件,开始一个新的记账旅程,对于理财开支,有个新的规划。通过小红书视频软件,学习了不少育儿知识,和各种不同的美食,以后动手制作,给宝宝做健康美味的营养餐。学习方面,继续学英语吧!虽然是抽出时间学的,进度也比较慢,但是积</div>
                    </li>
                    <li><a href="/article/1950218946015719424.htm"
                           title="图论算法经典题目解析:DFS、BFS与拓扑排序实战" target="_blank">图论算法经典题目解析:DFS、BFS与拓扑排序实战</a>
                        <span class="text-muted">周童學</span>
<a class="tag" taget="_blank" href="/search/%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84%E4%B8%8E%E7%AE%97%E6%B3%95/1.htm">数据结构与算法</a><a class="tag" taget="_blank" href="/search/%E6%B7%B1%E5%BA%A6%E4%BC%98%E5%85%88/1.htm">深度优先</a><a class="tag" taget="_blank" href="/search/%E7%AE%97%E6%B3%95/1.htm">算法</a><a class="tag" taget="_blank" href="/search/%E5%9B%BE%E8%AE%BA/1.htm">图论</a>
                        <div>图论算法经典题目解析:DFS、BFS与拓扑排序实战图论问题是算法面试中的高频考点,本博客将通过四道LeetCode经典题目(均来自"Top100Liked"题库),深入讲解图论的核心算法思想和实现技巧。涵盖DFS、BFS、拓扑排序和前缀树等知识点,每道题配有Java实现和易错点分析。1.岛屿数量(DFS遍历)问题描述给定一个由'1'(陆地)和'0'(水)组成的二维网格,计算岛屿的数量。岛屿由水平或</div>
                    </li>
                    <li><a href="/article/1950218652724817920.htm"
                           title="【 焦点咨询的“无为”】邹庆会,持续分享第690天,2020年1月23日" target="_blank">【 焦点咨询的“无为”】邹庆会,持续分享第690天,2020年1月23日</a>
                        <span class="text-muted">邹庆会</span>

                        <div>焦点课堂上,刘老师强调,焦点咨询师要“无为”,当时我就很困惑:我们“无为”,我们什么都不做,那来访者找我们做什么呢?那我们又怎么样来引领来访者呢?又怎么样让来访者在咨询当中有更多的收获呢?带着这个困惑,我逐渐在咨询中,包括在陪伴儿子的过程中,试着慢慢地放下期待、忘掉技术,寻找“无为”的感觉,寻找“无为”的痕迹,以及“无为”之后的一些效果的呈现。也慢慢的悟出一些自己的感受和体会。就像《道德经》中所说</div>
                    </li>
                    <li><a href="/article/1950218018411835392.htm"
                           title="D2早课与活力链接" target="_blank">D2早课与活力链接</a>
                        <span class="text-muted">亲爱的lingling</span>

                        <div>宇宙法则是:关注什么,什么就会变大。所以时刻关注自己在想什么,听什么,看什么!感恩今天早晨醒来的第一个意识是,真好,美好的一天开始了,我要越来越漂亮。起床做感恩冥想,呼吸法,喝一杯白开水,贴牛奶面膜。谢谢真我,感觉真好!感恩今天芳哥哥做的爱心早餐,给我煎了鸡蛋,谢谢芳哥的付出。谢谢!感恩我能够越来越清晰自己要做什么,越来越清楚知道自己想要的是什么,更加宁静与喜悦。今天早晨我听到我的高级智慧的声音,</div>
                    </li>
                    <li><a href="/article/1950217889994829824.htm"
                           title="践行8.0~第六周11.25-12.02" target="_blank">践行8.0~第六周11.25-12.02</a>
                        <span class="text-muted">初队长</span>

                        <div>突破后的喜悦最可怕的不是自己不清楚,而是自己清楚了,却依然不心动,我想这就是我们每个人的惰性存在,在这一周的践行,我发现自己依然是停留在自己的模式当中,不断的恶性的轮回,虽然的话,那再晨间日记方面是纸质的填写,但是对一天的工作没有起到应有的计划和推动的作用而我自己呢,也有些时候的话会处于一个相对来讲放松的一个状态,时间的把控的话也有一些点的消极,所以在这周的间隙,重点是关注自己的三大目标为目标来进</div>
                    </li>
                    <li><a href="/article/1950217809610993664.htm"
                           title="分支和循环(下)" target="_blank">分支和循环(下)</a>
                        <span class="text-muted">tryxr</span>
<a class="tag" taget="_blank" href="/search/%E6%9C%8D%E5%8A%A1%E5%99%A8/1.htm">服务器</a><a class="tag" taget="_blank" href="/search/%E8%BF%90%E7%BB%B4/1.htm">运维</a>
                        <div>写⼀个猜数字游戏游戏要求:1.电脑⾃动⽣成1~100的随机数2.玩家猜数字,猜数字的过程中,根据猜测数据的⼤⼩给出⼤了或⼩了的反馈,直到猜对,游戏结束1.随机数生成要想完成猜数字游戏,⾸先得产⽣随机数,那怎么产⽣随机数呢?randC语⾔提供了⼀个函数叫rand,这函数是可以⽣成随机数的,函数原型如下所⽰:intrand(void);rand函数会返回⼀个伪随机数,这个随机数的范围是在0~RAND_</div>
                    </li>
                    <li><a href="/article/1950215985592070144.htm"
                           title="我是孩子妈妈,我会让孩子饿着吗?" target="_blank">我是孩子妈妈,我会让孩子饿着吗?</a>
                        <span class="text-muted">松玲子</span>

                        <div>回老家过年,就是一场在关于喂养孩子问题上与老人的巅峰对决。前天我们回老家了,他爷爷奶奶就说孩子瘦了,就说我喂的不好,不按时喂,第一天夜里孩子总是睡一会就哭,睡一会就哭,夜里不知醒了多少次,弄得我真是几乎彻夜未眠。一大早,我还没起,我就听见他爷爷奶奶在外边说,今黑夜阳阳怎么老哭,是不是饿的,然后又延伸到我喂养的问题上,说不吃盐不行,不吃盐孩子没劲,吃蛋光吃个蛋黄,吃不饱,给他吃全蛋就行,哎呀我去,我</div>
                    </li>
                    <li><a href="/article/1950215036291051520.htm"
                           title="北斗短报文兜底、5G-A增强:AORO P1100三防平板构建应急通信网络" target="_blank">北斗短报文兜底、5G-A增强:AORO P1100三防平板构建应急通信网络</a>
                        <span class="text-muted"></span>

                        <div>公网中断的灾区现场,泥石流阻断了最后一条光缆。一支救援队却在废墟间有序穿行,队长手中的三防平板正闪烁着北斗卫星信号,定位坐标与伤亡信息化作一行行短报文,穿透通信孤岛直达指挥中心。这是AOROP1100三防平板搭载的北斗短报文功能在应急救援中的真实场景,更代表了工业移动终端在极端环境下的能力跃迁。AOROP1100三防平板作为遨游通讯2025年推出的旗舰三防设备,AOROP1100三防平板的技术基底</div>
                    </li>
                    <li><a href="/article/1950212289357475840.htm"
                           title="“不经一番寒彻骨,哪得梅花扑鼻香”" target="_blank">“不经一番寒彻骨,哪得梅花扑鼻香”</a>
                        <span class="text-muted">蹦吧卡拉拉</span>

                        <div>沉默是一种历练,一种彻悟,一种对生活的宽容与超脱。掌握了沉默拥有的力量,就能让我们适应变化莫测的生活,让我们在复杂的环境里学会自我保护,并在无声的世界里实现真正的自我超越。在等待中积蓄力量生活中,我们几乎每一天都在等待:小孩子哭哭啼啼,那是在等待着父母回家陪他一起玩耍;老人整日望眼欲穿,那是等待着远方的孩子早日回家团聚;怀揣创业梦的年轻人整日风餐露宿,食不果腹,那是在等待着一飞冲天的机遇实现自己的</div>
                    </li>
                    <li><a href="/article/1950212288136933376.htm"
                           title="今日随笔" target="_blank">今日随笔</a>
                        <span class="text-muted">小小林_005b</span>

                        <div>2019.10.21.周一晴全职第436天50+21/day118天【皮皮第118天】1.昨晚闹腾到一点多才安稳入睡,一个晚上一直哭哭闹闹(´;︵;`),没睡一会儿就会惊吓大哭(´;︵;`),一直抱着哄,似乎抱着才更加有安全感才能睡得更好。小胖子越来越重,我的手和腰部有些承受不了,经常腰酸痛到直不起来,好在有黑先生和啊影子下班后有空了就帮我抱一会儿。2.今日排便三次,一次偏向绿色,一两次金黄色。3</div>
                    </li>
                    <li><a href="/article/1950212284320116736.htm"
                           title="漫步,跳出藩篱" target="_blank">漫步,跳出藩篱</a>
                        <span class="text-muted">张巧金沙</span>

                        <div>最近的教学,倍感不爽。一为这国庆之假,把这课上得支离破碎的。放假前,上了四天课,但我却只上了三天,9月30日,我工作室在搞活动,全天的活动,课当然未能上。10月8日学生回校,上了两天课,学生又放回家了。就觉得学生刚有点状态,又回去逍遥去了。感觉吧,教学内容也不敢大胆甩开膀子去教学,所以呀,这教学内容还真上不走,而且学生学下来效果特差。这不,国庆放假前的一个周,测试了两次,均为第一单元,是自考试以来</div>
                    </li>
                    <li><a href="/article/1950208983868436480.htm"
                           title="2018-08-29精进打卡" target="_blank">2018-08-29精进打卡</a>
                        <span class="text-muted">米兰王</span>

                        <div>姓名:王兰英【日精进打卡第25天】【知~学习】《六项精进》1遍共39遍《大学》1遍共50遍【经典名句分享】一切都是最好的安排。【行~实践】一、修身:(对自己个人)1,散步1小时。2,每天坚持读书。二、齐家:(对家庭和家人)1,指导孩子开车。2,和家人一起逛超市。三、建功:(对工作)用心做好每件事。{积善}:发愿从2018年8月5日起1年内365个善事。今日1善,累计27善。【省~觉悟】正人先正己。</div>
                    </li>
                    <li><a href="/article/1950208107430866944.htm"
                           title="python笔记14介绍几个魔法方法" target="_blank">python笔记14介绍几个魔法方法</a>
                        <span class="text-muted">抢公主的大魔王</span>
<a class="tag" taget="_blank" href="/search/python/1.htm">python</a><a class="tag" taget="_blank" href="/search/python/1.htm">python</a>
                        <div>python笔记14介绍几个魔法方法先声明一下各位大佬,这是我的笔记。如有错误,恳请指正。另外,感谢您的观看,谢谢啦!(1).__doc__输出对应的函数,类的说明文档print(print.__doc__)print(value,...,sep='',end='\n',file=sys.stdout,flush=False)Printsthevaluestoastream,ortosys.std</div>
                    </li>
                    <li><a href="/article/1950207970721722368.htm"
                           title="老公的女朋友把我打成小三后,我杀疯了周昊净许青青小说完结推荐_最热门小说 老公的女朋友把我打成小三后,我杀疯了周昊净许青青" target="_blank">老公的女朋友把我打成小三后,我杀疯了周昊净许青青小说完结推荐_最热门小说 老公的女朋友把我打成小三后,我杀疯了周昊净许青青</a>
                        <span class="text-muted">小富江呀</span>

                        <div>《老公的女朋友把我打成小三后,我杀疯了》主角:周昊净许青青简介:只因跟老公说了几句情话,就被老公的‘女朋友’当成小三。她带着一群自诩为“惩治小三联盟”的网络判官冲进了我家。“怎么,有脸当小三,没脸承认?”“从你当小三的那一刻起,就该想到会有被人收拾的一天!”“我们网络判官专治道德败坏的贱人!”这群人一边疯狂大骂,一边愤怒打砸。看着狼藉不堪的家,我面色平静地给公司法务部发去消息。“按照婚前协议,拟一</div>
                    </li>
                    <li><a href="/article/1950207972055511040.htm"
                           title="2021-10-26 躺平日记:18.《陀枪师姐》" target="_blank">2021-10-26 躺平日记:18.《陀枪师姐》</a>
                        <span class="text-muted">春迟馆</span>

                        <div>写了一天字,明天《道德经》就可以临完了。阳台的玻璃也擦完了,明天再收拾收拾花盆什么的,阳台就基本告一段落。不管干活还是写字,总是用老剧做背景声音。因为看过,所以有一眼没一眼都无所谓,主要作用一是可以计时,一是提醒自己每集播完都起身活动活动。这几天放的是《陀枪师姐》。看朱素娥一步步从一个生活、事业陷入困境的绝望主妇,通过努力,不断提升自己,成长为优秀的配枪女警,真是很励志。</div>
                    </li>
                                <li><a href="/article/55.htm"
                                       title="多线程编程之卫生间" target="_blank">多线程编程之卫生间</a>
                                    <span class="text-muted">周凡杨</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a><a class="tag" taget="_blank" href="/search/%E5%B9%B6%E5%8F%91/1.htm">并发</a><a class="tag" taget="_blank" href="/search/%E5%8D%AB%E7%94%9F%E9%97%B4/1.htm">卫生间</a><a class="tag" taget="_blank" href="/search/%E7%BA%BF%E7%A8%8B/1.htm">线程</a><a class="tag" taget="_blank" href="/search/%E5%8E%95%E6%89%80/1.htm">厕所</a>
                                    <div>如大家所知,火车上车厢的卫生间很小,每次只能容纳一个人,一个车厢只有一个卫生间,这个卫生间会被多个人同时使用,在实际使用时,当一个人进入卫生间时则会把卫生间锁上,等出来时打开门,下一个人进去把门锁上,如果有一个人在卫生间内部则别人的人发现门是锁的则只能在外面等待。问题分析:首先问题中有两个实体,一个是人,一个是厕所,所以设计程序时就可以设计两个类。人是多数的,厕所只有一个(暂且模拟的是一个车厢)。</div>
                                </li>
                                <li><a href="/article/182.htm"
                                       title="How to Install GUI to Centos Minimal" target="_blank">How to Install GUI to Centos Minimal</a>
                                    <span class="text-muted">sunjing</span>
<a class="tag" taget="_blank" href="/search/linux/1.htm">linux</a><a class="tag" taget="_blank" href="/search/Install/1.htm">Install</a><a class="tag" taget="_blank" href="/search/Desktop/1.htm">Desktop</a><a class="tag" taget="_blank" href="/search/GUI/1.htm">GUI</a>
                                    <div>http://www.namhuy.net/475/how-to-install-gui-to-centos-minimal.html 
  
I have centos 6.3 minimal running as web server. I’m looking to install gui to my server to vnc to my server. You can insta</div>
                                </li>
                                <li><a href="/article/309.htm"
                                       title="Shell 函数" target="_blank">Shell 函数</a>
                                    <span class="text-muted">daizj</span>
<a class="tag" taget="_blank" href="/search/shell/1.htm">shell</a><a class="tag" taget="_blank" href="/search/%E5%87%BD%E6%95%B0/1.htm">函数</a>
                                    <div>Shell 函数 
linux shell 可以用户定义函数,然后在shell脚本中可以随便调用。 
shell中函数的定义格式如下: 
[function] funname [()]{

    action;
  
     [return int;]

} 
说明: 
 
 1、可以带function fun() 定义,也可以直接fun() 定义,不带任何参数。 
 2、参数返回</div>
                                </li>
                                <li><a href="/article/436.htm"
                                       title="Linux服务器新手操作之一" target="_blank">Linux服务器新手操作之一</a>
                                    <span class="text-muted">周凡杨</span>
<a class="tag" taget="_blank" href="/search/Linux+%E7%AE%80%E5%8D%95+%E6%93%8D%E4%BD%9C/1.htm">Linux 简单 操作</a>
                                    <div>1.whoami 
     当一个用户登录Linux系统之后,也许他想知道自己是发哪个用户登录的。 
     此时可以使用whoami命令。 
     [ecuser@HA5-DZ05 ~]$ whoami 
      e</div>
                                </li>
                                <li><a href="/article/563.htm"
                                       title="浅谈Socket通信(一)" target="_blank">浅谈Socket通信(一)</a>
                                    <span class="text-muted">朱辉辉33</span>
<a class="tag" taget="_blank" href="/search/socket/1.htm">socket</a>
                                    <div>在java中ServerSocket用于服务器端,用来监听端口。通过服务器监听,客户端发送请求,双方建立链接后才能通信。当服务器和客户端建立链接后,两边都会产生一个Socket实例,我们可以通过操作Socket来建立通信。 
   首先我建立一个ServerSocket对象。当然要导入java.net.ServerSocket包 
   ServerSock</div>
                                </li>
                                <li><a href="/article/690.htm"
                                       title="关于框架的简单认识" target="_blank">关于框架的简单认识</a>
                                    <span class="text-muted">西蜀石兰</span>
<a class="tag" taget="_blank" href="/search/%E6%A1%86%E6%9E%B6/1.htm">框架</a>
                                    <div>入职两个月多,依然是一个不会写代码的小白,每天的工作就是看代码,写wiki。 
前端接触CSS、HTML、JS等语言,一直在用的CS模型,自然免不了数据库的链接及使用,真心涉及框架,项目中用到的BootStrap算一个吧,哦,JQuery只能算半个框架吧,我更觉得它是另外一种语言。 
后台一直是纯Java代码,涉及的框架是Quzrtz和log4j。 
 
都说学前端的要知道三大框架,目前node.</div>
                                </li>
                                <li><a href="/article/817.htm"
                                       title="You have an error in your SQL syntax; check the manual that corresponds to your" target="_blank">You have an error in your SQL syntax; check the manual that corresponds to your</a>
                                    <span class="text-muted">林鹤霄</span>

                                    <div>You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'option,changed_ids  ) values('0ac91f167f754c8cbac00e9e3dc372</div>
                                </li>
                                <li><a href="/article/944.htm"
                                       title="MySQL5.6的my.ini配置" target="_blank">MySQL5.6的my.ini配置</a>
                                    <span class="text-muted">aigo</span>
<a class="tag" taget="_blank" href="/search/mysql/1.htm">mysql</a>
                                    <div>注意:以下配置的服务器硬件是:8核16G内存  
  
[client] 
  
port=3306 
  
[mysql] 
  
default-character-set=utf8 
  
  
[mysqld] 
  
port=3306 
  
basedir=D:/mysql-5.6.21-win</div>
                                </li>
                                <li><a href="/article/1071.htm"
                                       title="mysql 全文模糊查找 便捷解决方案" target="_blank">mysql 全文模糊查找 便捷解决方案</a>
                                    <span class="text-muted">alxw4616</span>
<a class="tag" taget="_blank" href="/search/mysql/1.htm">mysql</a>
                                    <div>mysql 全文模糊查找 便捷解决方案 
2013/6/14 by 半仙 alxw4616@Msn.com 
 
目的: 项目需求实现模糊查找. 
原则: 查询不能超过 1秒. 
 
问题: 目标表中有超过1千万条记录. 使用like '%str%' 进行模糊查询无法达到性能需求. 
解决方案: 使用mysql全文索引. 
 1.全文索引 : MySQL支持全文索引和搜索功能。MySQL中的全文索</div>
                                </li>
                                <li><a href="/article/1198.htm"
                                       title="自定义数据结构 链表(单项 ,双向,环形)" target="_blank">自定义数据结构 链表(单项 ,双向,环形)</a>
                                    <span class="text-muted">百合不是茶</span>
<a class="tag" taget="_blank" href="/search/%E5%8D%95%E9%A1%B9%E9%93%BE%E8%A1%A8/1.htm">单项链表</a><a class="tag" taget="_blank" href="/search/%E5%8F%8C%E5%90%91%E9%93%BE%E8%A1%A8/1.htm">双向链表</a>
                                    <div>  
   链表与动态数组的实现方式差不多,    数组适合快速删除某个元素    链表则可以快速的保存数组并且可以是不连续的 
  
    
单项链表;数据从第一个指向最后一个 
  
实现代码: 
  
     
//定义动态链表
clas</div>
                                </li>
                                <li><a href="/article/1325.htm"
                                       title="threadLocal实例" target="_blank">threadLocal实例</a>
                                    <span class="text-muted">bijian1013</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a><a class="tag" taget="_blank" href="/search/thread/1.htm">thread</a><a class="tag" taget="_blank" href="/search/java%E5%A4%9A%E7%BA%BF%E7%A8%8B/1.htm">java多线程</a><a class="tag" taget="_blank" href="/search/threadLocal/1.htm">threadLocal</a>
                                    <div>实例1: 
package com.bijian.thread;

public class MyThread extends Thread {

	private static ThreadLocal tl = new ThreadLocal() {
		protected synchronized Object initialValue() {
			return new Inte</div>
                                </li>
                                <li><a href="/article/1452.htm"
                                       title="activemq安全设置—设置admin的用户名和密码" target="_blank">activemq安全设置—设置admin的用户名和密码</a>
                                    <span class="text-muted">bijian1013</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a><a class="tag" taget="_blank" href="/search/activemq/1.htm">activemq</a>
                                    <div>        ActiveMQ使用的是jetty服务器, 打开conf/jetty.xml文件,找到 
<bean id="adminSecurityConstraint" class="org.eclipse.jetty.util.security.Constraint">
        <p</div>
                                </li>
                                <li><a href="/article/1579.htm"
                                       title="【Java范型一】Java范型详解之范型集合和自定义范型类" target="_blank">【Java范型一】Java范型详解之范型集合和自定义范型类</a>
                                    <span class="text-muted">bit1129</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a>
                                    <div>本文详细介绍Java的范型,写一篇关于范型的博客原因有两个,前几天要写个范型方法(返回值根据传入的类型而定),竟然想了半天,最后还是从网上找了个范型方法的写法;再者,前一段时间在看Gson, Gson这个JSON包的精华就在于对范型的优雅简单的处理,看它的源代码就比较迷糊,只其然不知其所以然。所以,还是花点时间系统的整理总结下范型吧。 
  范型内容 
 
 范型集合类 
 范型类 
 </div>
                                </li>
                                <li><a href="/article/1706.htm"
                                       title="【HBase十二】HFile存储的是一个列族的数据" target="_blank">【HBase十二】HFile存储的是一个列族的数据</a>
                                    <span class="text-muted">bit1129</span>
<a class="tag" taget="_blank" href="/search/hbase/1.htm">hbase</a>
                                    <div>在HBase中,每个HFile存储的是一个表中一个列族的数据,也就是说,当一个表中有多个列簇时,针对每个列簇插入数据,最后产生的数据是多个HFile,每个对应一个列族,通过如下操作验证 
  
1. 建立一个有两个列族的表 
  
create 'members','colfam1','colfam2' 
  
2. 在members表中的colfam1中插入50*5</div>
                                </li>
                                <li><a href="/article/1833.htm"
                                       title="Nginx 官方一个配置实例" target="_blank">Nginx 官方一个配置实例</a>
                                    <span class="text-muted">ronin47</span>
<a class="tag" taget="_blank" href="/search/nginx+%E9%85%8D%E7%BD%AE%E5%AE%9E%E4%BE%8B/1.htm">nginx 配置实例</a>
                                    <div>user       www www;
worker_processes  5;
error_log  logs/error.log;
pid        logs/nginx.pid;
worker_rlimit_nofile 8192;

events {
  worker_connections  4096;}

http {
  include    conf/mim</div>
                                </li>
                                <li><a href="/article/1960.htm"
                                       title="java-15.输入一颗二元查找树,将该树转换为它的镜像, 即在转换后的二元查找树中,左子树的结点都大于右子树的结点。 用递归和循环" target="_blank">java-15.输入一颗二元查找树,将该树转换为它的镜像, 即在转换后的二元查找树中,左子树的结点都大于右子树的结点。 用递归和循环</a>
                                    <span class="text-muted">bylijinnan</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a>
                                    <div>
//use recursion
	public static void mirrorHelp1(Node node){
		if(node==null)return;
		swapChild(node);
		mirrorHelp1(node.getLeft());
		mirrorHelp1(node.getRight());
	}
	//use no recursion bu</div>
                                </li>
                                <li><a href="/article/2087.htm"
                                       title="返回null还是empty" target="_blank">返回null还是empty</a>
                                    <span class="text-muted">bylijinnan</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a><a class="tag" taget="_blank" href="/search/apache/1.htm">apache</a><a class="tag" taget="_blank" href="/search/spring/1.htm">spring</a><a class="tag" taget="_blank" href="/search/%E7%BC%96%E7%A8%8B/1.htm">编程</a>
                                    <div>第一个问题,函数是应当返回null还是长度为0的数组(或集合)? 
第二个问题,函数输入参数不当时,是异常还是返回null? 
 
先看第一个问题 
 
有两个约定我觉得应当遵守: 
 
1.返回零长度的数组或集合而不是null(详见《Effective Java》) 
 
理由就是,如果返回empty,就可以少了很多not-null判断: 
 

List<Person> list</div>
                                </li>
                                <li><a href="/article/2214.htm"
                                       title="[科技与项目]工作流厂商的战略机遇期" target="_blank">[科技与项目]工作流厂商的战略机遇期</a>
                                    <span class="text-muted">comsci</span>
<a class="tag" taget="_blank" href="/search/%E5%B7%A5%E4%BD%9C%E6%B5%81/1.htm">工作流</a>
                                    <div> 
 
      在新的战略平衡形成之前,这里有一个短暂的战略机遇期,只有大概最短6年,最长14年的时间,这段时间就好像我们森林里面的小动物,在秋天中,必须抓紧一切时间存储坚果一样,否则无法熬过漫长的冬季。。。。 
 
 
        在微软,甲骨文,谷歌,IBM,SONY</div>
                                </li>
                                <li><a href="/article/2341.htm"
                                       title="过度设计-举例" target="_blank">过度设计-举例</a>
                                    <span class="text-muted">cuityang</span>
<a class="tag" taget="_blank" href="/search/%E8%BF%87%E5%BA%A6%E8%AE%BE%E8%AE%A1/1.htm">过度设计</a>
                                    <div>过度设计,需要更多设计时间和测试成本,如无必要,还是尽量简洁一些好。 
未来的事情,比如 访问量,比如数据库的容量,比如是否需要改成分布式  都是无法预料的 
 
再举一个例子,对闰年的判断逻辑: 
  1、 if($Year%4==0) return True; else return Fasle; 
  2、if (   ($Year%4==0  &am</div>
                                </li>
                                <li><a href="/article/2468.htm"
                                       title="java进阶,《Java性能优化权威指南》试读" target="_blank">java进阶,《Java性能优化权威指南》试读</a>
                                    <span class="text-muted">darkblue086</span>
<a class="tag" taget="_blank" href="/search/java%E6%80%A7%E8%83%BD%E4%BC%98%E5%8C%96/1.htm">java性能优化</a>
                                    <div>记得当年随意读了微软出版社的.NET 2.0应用程序调试,才发现调试器如此强大,应用程序开发调试其实真的简单了很多,不仅仅是因为里面介绍了很多调试器工具的使用,更是因为里面寻找问题并重现问题的思想让我震撼,时隔多年,Java已经如日中天,成为许多大型企业应用的首选,而今天,这本《Java性能优化权威指南》让我再次找到了这种感觉,从不经意的开发过程让我刮目相看,原来性能调优不是简单地看看热点在哪里,</div>
                                </li>
                                <li><a href="/article/2595.htm"
                                       title="网络学习笔记初识OSI七层模型与TCP协议" target="_blank">网络学习笔记初识OSI七层模型与TCP协议</a>
                                    <span class="text-muted">dcj3sjt126com</span>
<a class="tag" taget="_blank" href="/search/%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/1.htm">学习笔记</a>
                                    <div>   协议:在计算机网络中通信各方面所达成的、共同遵守和执行的一系列约定     计算机网络的体系结构:计算机网络的层次结构和各层协议的集合。     两类服务:     面向连接的服务通信双方在通信之前先建立某种状态,并在通信过程中维持这种状态的变化,同时为服务对象预先分配一定的资源。这种服务叫做面向连接的服务。     面向无连接的服务通信双方在通信前后不建立和维持状态,不为服务对象</div>
                                </li>
                                <li><a href="/article/2722.htm"
                                       title="mac中用命令行运行mysql" target="_blank">mac中用命令行运行mysql</a>
                                    <span class="text-muted">dcj3sjt126com</span>
<a class="tag" taget="_blank" href="/search/mysql/1.htm">mysql</a><a class="tag" taget="_blank" href="/search/linux/1.htm">linux</a><a class="tag" taget="_blank" href="/search/mac/1.htm">mac</a>
                                    <div>参考这篇博客:http://www.cnblogs.com/macro-cheng/archive/2011/10/25/mysql-001.html  感觉workbench不好用(有点先入为主了)。 
1,安装mysql 
在mysql的官方网站下载 mysql 5.5.23 http://www.mysql.com/downloads/mysql/,根据我的机器的配置情况选择了64</div>
                                </li>
                                <li><a href="/article/2849.htm"
                                       title="MongDB查询(1)——基本查询[五]" target="_blank">MongDB查询(1)——基本查询[五]</a>
                                    <span class="text-muted">eksliang</span>
<a class="tag" taget="_blank" href="/search/mongodb/1.htm">mongodb</a><a class="tag" taget="_blank" href="/search/mongodb+%E6%9F%A5%E8%AF%A2/1.htm">mongodb 查询</a><a class="tag" taget="_blank" href="/search/mongodb+find/1.htm">mongodb find</a>
                                    <div>MongDB查询 
转载请出自出处:http://eksliang.iteye.com/blog/2174452 一、find简介 
MongoDB中使用find来进行查询。 
API:如下 
function ( query , fields , limit , skip, batchSize, options ){.....} 
 参数含义: 
 
 query:查询参数 
 fie</div>
                                </li>
                                <li><a href="/article/2976.htm"
                                       title="base64,加密解密 经融加密,对接" target="_blank">base64,加密解密 经融加密,对接</a>
                                    <span class="text-muted">y806839048</span>
<a class="tag" taget="_blank" href="/search/%E7%BB%8F%E8%9E%8D%E5%8A%A0%E5%AF%86/1.htm">经融加密</a><a class="tag" taget="_blank" href="/search/%E5%AF%B9%E6%8E%A5/1.htm">对接</a>
                                    <div>String data0 = new String(Base64.encode(bo.getPaymentResult().getBytes(("GBK")))); 
 String data1 = new String(Base64.decode(data0.toCharArray()),"GBK"); 
 
// 注意编码格式,注意用于加密,解密的要是同</div>
                                </li>
                                <li><a href="/article/3103.htm"
                                       title="JavaWeb之JSP概述" target="_blank">JavaWeb之JSP概述</a>
                                    <span class="text-muted">ihuning</span>
<a class="tag" taget="_blank" href="/search/javaweb/1.htm">javaweb</a>
                                    <div>  
什么是JSP?为什么使用JSP? 
JSP表示Java Server Page,即嵌有Java代码的HTML页面。使用JSP是因为在HTML中嵌入Java代码比在Java代码中拼接字符串更容易、更方便和更高效。 
  
JSP起源  
  
在很多动态网页中,绝大部分内容都是固定不变的,只有局部内容需要动态产生和改变。  
如果使用Servl</div>
                                </li>
                                <li><a href="/article/3230.htm"
                                       title="apple watch 指南" target="_blank">apple watch 指南</a>
                                    <span class="text-muted">啸笑天</span>
<a class="tag" taget="_blank" href="/search/apple/1.htm">apple</a>
                                    <div>1. 文档 
 
  WatchKit Programming Guide(中译在线版 By @CocoaChina)    译文 译者 原文   概览 - 开始为 Apple Watch 进行开发 @星夜暮晨 Overview - Developing for Apple Watch   概览 - 配置 Xcode 项目 - Overview - Configuring Yo</div>
                                </li>
                                <li><a href="/article/3357.htm"
                                       title="java经典的基础题目" target="_blank">java经典的基础题目</a>
                                    <span class="text-muted">macroli</span>
<a class="tag" taget="_blank" href="/search/java/1.htm">java</a><a class="tag" taget="_blank" href="/search/%E7%BC%96%E7%A8%8B/1.htm">编程</a>
                                    <div>1.列举出 10个JAVA语言的优势 a:免费,开源,跨平台(平台独立性),简单易用,功能完善,面向对象,健壮性,多线程,结构中立,企业应用的成熟平台, 无线应用 2.列举出JAVA中10个面向对象编程的术语 a:包,类,接口,对象,属性,方法,构造器,继承,封装,多态,抽象,范型 3.列举出JAVA中6个比较常用的包 Java.lang;java.util;java.io;java.sql;ja</div>
                                </li>
                                <li><a href="/article/3484.htm"
                                       title="你所不知道神奇的js replace正则表达式" target="_blank">你所不知道神奇的js replace正则表达式</a>
                                    <span class="text-muted">qiaolevip</span>
<a class="tag" taget="_blank" href="/search/%E6%AF%8F%E5%A4%A9%E8%BF%9B%E6%AD%A5%E4%B8%80%E7%82%B9%E7%82%B9/1.htm">每天进步一点点</a><a class="tag" taget="_blank" href="/search/%E5%AD%A6%E4%B9%A0%E6%B0%B8%E6%97%A0%E6%AD%A2%E5%A2%83/1.htm">学习永无止境</a><a class="tag" taget="_blank" href="/search/%E7%BA%B5%E8%A7%82%E5%8D%83%E8%B1%A1/1.htm">纵观千象</a><a class="tag" taget="_blank" href="/search/regex/1.htm">regex</a>
                                    <div>var v = 'C9CFBAA3CAD0';
console.log(v);
var arr = v.split('');
for (var i = 0; i < arr.length; i ++) {
  if (i % 2 == 0) arr[i] = '%' + arr[i];
}
console.log(arr.join(''));

console.log(v.r</div>
                                </li>
                                <li><a href="/article/3611.htm"
                                       title="[一起学Hive]之十五-分析Hive表和分区的统计信息(Statistics)" target="_blank">[一起学Hive]之十五-分析Hive表和分区的统计信息(Statistics)</a>
                                    <span class="text-muted">superlxw1234</span>
<a class="tag" taget="_blank" href="/search/hive/1.htm">hive</a><a class="tag" taget="_blank" href="/search/hive%E5%88%86%E6%9E%90%E8%A1%A8/1.htm">hive分析表</a><a class="tag" taget="_blank" href="/search/hive%E7%BB%9F%E8%AE%A1%E4%BF%A1%E6%81%AF/1.htm">hive统计信息</a><a class="tag" taget="_blank" href="/search/hive+Statistics/1.htm">hive Statistics</a>
                                    <div>关键字:Hive统计信息、分析Hive表、Hive Statistics 
  
类似于Oracle的分析表,Hive中也提供了分析表和分区的功能,通过自动和手动分析Hive表,将Hive表的一些统计信息存储到元数据中。 
  
表和分区的统计信息主要包括:行数、文件数、原始数据大小、所占存储大小、最后一次操作时间等; 
  14.1 新表的统计信息 
对于一个新创建</div>
                                </li>
                                <li><a href="/article/3738.htm"
                                       title="Spring Boot 1.2.5 发布" target="_blank">Spring Boot 1.2.5 发布</a>
                                    <span class="text-muted">wiselyman</span>
<a class="tag" taget="_blank" href="/search/spring+boot/1.htm">spring boot</a>
                                    <div>  
  
Spring Boot 1.2.5已在7月2日发布,现在可以从spring的maven库和maven中心库下载。 
  
这个版本是一个维护的发布版,主要是一些修复以及将Spring的依赖提升至4.1.7(包含重要的安全修复)。 
  
官方建议所有的Spring Boot用户升级这个版本。 
  
项目首页 | 源</div>
                                </li>
                </ul>
            </div>
        </div>
    </div>

<div>
    <div class="container">
        <div class="indexes">
            <strong>按字母分类:</strong>
            <a href="/tags/A/1.htm" target="_blank">A</a><a href="/tags/B/1.htm" target="_blank">B</a><a href="/tags/C/1.htm" target="_blank">C</a><a
                href="/tags/D/1.htm" target="_blank">D</a><a href="/tags/E/1.htm" target="_blank">E</a><a href="/tags/F/1.htm" target="_blank">F</a><a
                href="/tags/G/1.htm" target="_blank">G</a><a href="/tags/H/1.htm" target="_blank">H</a><a href="/tags/I/1.htm" target="_blank">I</a><a
                href="/tags/J/1.htm" target="_blank">J</a><a href="/tags/K/1.htm" target="_blank">K</a><a href="/tags/L/1.htm" target="_blank">L</a><a
                href="/tags/M/1.htm" target="_blank">M</a><a href="/tags/N/1.htm" target="_blank">N</a><a href="/tags/O/1.htm" target="_blank">O</a><a
                href="/tags/P/1.htm" target="_blank">P</a><a href="/tags/Q/1.htm" target="_blank">Q</a><a href="/tags/R/1.htm" target="_blank">R</a><a
                href="/tags/S/1.htm" target="_blank">S</a><a href="/tags/T/1.htm" target="_blank">T</a><a href="/tags/U/1.htm" target="_blank">U</a><a
                href="/tags/V/1.htm" target="_blank">V</a><a href="/tags/W/1.htm" target="_blank">W</a><a href="/tags/X/1.htm" target="_blank">X</a><a
                href="/tags/Y/1.htm" target="_blank">Y</a><a href="/tags/Z/1.htm" target="_blank">Z</a><a href="/tags/0/1.htm" target="_blank">其他</a>
        </div>
    </div>
</div>
<footer id="footer" class="mb30 mt30">
    <div class="container">
        <div class="footBglm">
            <a target="_blank" href="/">首页</a> -
            <a target="_blank" href="/custom/about.htm">关于我们</a> -
            <a target="_blank" href="/search/Java/1.htm">站内搜索</a> -
            <a target="_blank" href="/sitemap.txt">Sitemap</a> -
            <a target="_blank" href="/custom/delete.htm">侵权投诉</a>
        </div>
        <div class="copyright">版权所有 IT知识库 CopyRight © 2000-2050 E-COM-NET.COM , All Rights Reserved.
<!--            <a href="https://beian.miit.gov.cn/" rel="nofollow" target="_blank">京ICP备09083238号</a><br>-->
        </div>
    </div>
</footer>
<!-- 代码高亮 -->
<script type="text/javascript" src="/static/syntaxhighlighter/scripts/shCore.js"></script>
<script type="text/javascript" src="/static/syntaxhighlighter/scripts/shLegacy.js"></script>
<script type="text/javascript" src="/static/syntaxhighlighter/scripts/shAutoloader.js"></script>
<link type="text/css" rel="stylesheet" href="/static/syntaxhighlighter/styles/shCoreDefault.css"/>
<script type="text/javascript" src="/static/syntaxhighlighter/src/my_start_1.js"></script>





</body>

</html>