聊天模型--流式传输

一、stream() 同步传输

python 复制代码
from langchain_community.chat_models import ChatTongyi

#.stream() ⽅法返回⼀个迭代器,该迭代器在⽣成输出时同步产⽣输出 消息块 。可以使⽤ for 循环实时处理每个块

model = ChatTongyi(model="qwen-plus")

for chunk in model.stream("写一个1000字的作文"):
    print(chunk.content, end= "", flush=True)

二、astream() 异步传输

1.进程、线程、协程

进程:操作系统分配资源的基本单位,有独立内存空间,隔离性好,但创建和切换开销最大。适合需要强隔离,多核CPU密集计算的场景。

线程是操作系统调度的基本单位,属于某个进程,同一进程内线程共享内存,比进程轻量,但需要处理线程安全问题。适合I/O密集、并发量中等的场景。

协程是用户态的轻量级执行单元,由程序自己调度,不经过操作系统。切换成本极低,可创建大量协程,但采用协作式调度,只在主动让出(如await)时切换。适合高并发I/O场景,如网络请求,数据库查询。

关系:一个进程包含多个线程,一个线程可以运行多个协程。进程>线程>协程,粒度越来越细,开销越来越小。

python 复制代码
import asyncio
import time


#定义协程
async def boil_water_async():
    print("开始烧水...")
    await asyncio.sleep(5) # await表示这个操作完成,但期间让事件循环去做别的事
    print("水开了!")
async def send_message_saync():
    print("开始发短信...")
    await asyncio.sleep(2)
    print("发送消息成功!")
#主程序也是一个协程
async def main():
    current = time.time()
    task1 = asyncio.create_task(send_message_saync())
    task2 = asyncio.create_task(boil_water_async())
    #等待两个任务都完成
    await task1
    await task2
    end = time.time()
    print(f"总耗时:{end-current}")

asyncio.run(main())

2.大模型的异步使用

python 复制代码
import asyncio

from langchain_community.chat_models import ChatTongyi

model = ChatTongyi(model="qwen-plus", streaming=True)

async def async_stream():
    print("====异步调用====")
    async for chunk in model.astream("你是谁"):
        print(chunk.content, end="|", flush=True)

asyncio.run(async_stream())

三、自定义流式输出解析器

当一个函数包含 yield 时,调用该函数不会立即执行代码,而是返回一个生成器对象。只有当你遍历这个生成器(如使用 for 循环或 next())时,函数才会开始执行。

  • 执行到 yield 行时,函数会返回 后面的值,并冻结当前状态(记住所有局部变量)。

  • 下次调用 next() 时,函数会从刚才冻结的下一行 继续执行,直到再次遇到 yield 或结束。

python 复制代码
from typing import Iterable, List

from langchain_community.chat_models import ChatTongyi
from langchain_core.output_parsers import StrOutputParser

model = ChatTongyi(model="qwen-plus")

#定义输出解析器
parse = StrOutputParser()

def split_into_list(input: Iterable[str]) -> Iterable[List[str]]:
    """
    流式句子切分器:将模型逐段输出的文本,按中文句号「。」拆成完整句子。

    典型输入来自 LangChain 链式调用中的流式字符串(如 model | StrOutputParser)。
    每凑齐一句(遇到句号)就立即 yield,无需等待全文生成完毕。

    Args:
        input: 字符串可迭代对象,每次迭代得到一小段文本(一个 chunk)

    Yields:
        List[str]: 单元素列表,包含一句已去掉首尾空白的完整句子(不含句号)

    示例:
        输入流: "春眠" -> "不觉晓。" -> "处处闻啼鸟。"
        输出:   ["春眠不觉晓"] -> ["处处闻啼鸟"]
    """
    # 缓冲区:累积尚未形成完整句子的文本碎片
    # 模型流式输出时每次只给几个字,需要暂存到 buffer 中拼接
    buffer = ""

    # 遍历上游传来的每一个文本片段(流式 chunk)
    for chunk in input:
        # 将新片段追加到缓冲区末尾
        buffer += chunk

        # 用 while 而非 if:一个 chunk 可能包含多个句号(如 "A。B。C。"),
        # 需要循环切分,直到 buffer 中不再包含句号
        while "。" in buffer:
            # 找到第一个句号的位置,作为当前句子的结束边界
            stop_index = buffer.index("。")

            # 截取句号之前的内容作为一句,strip() 去掉首尾空白字符
            # 包装成单元素列表,符合 LangChain 链式输出的列表格式
            yield [buffer[:stop_index].strip()]

            # 保留句号之后的剩余文本,供下一句拼接使用(句号本身丢弃)
            buffer = buffer[stop_index + 1:]

    # 输入流结束后,若 buffer 中仍有内容(最后一句没有句号,或只剩空白),
    # 将剩余部分作为最后一条结果输出
    yield [buffer.strip()]


chain = model | parse | split_into_list

for chunk in chain.stream("给我写一首七言绝律诗词, 每句以句号分割"):
    print(chunk, end="|", flush=True)

四、SSE协议

SSE(Server-Sent Events)是⼀种基于 HTTP 的轻量级实时通信协议,浏览器可以通过内置的
EventSource API 接收并处理这些实时事件。

核⼼特点
基于 HTTP 协议
复⽤标准 HTTP/HTTPS 协议,⽆需额外端⼝或协议,兼容性好且易于部署。
单向通信机制
SSE 仅⽀持服务器向客⼾端的单向数据推送,客⼾端通过普通 HTTP 请求建⽴连接后,服务器可持续发送数据流,但客⼾端⽆法通过同⼀连接向服务器发送数据。
⾃动重连机制
⽀持断线重连,连接中断时,浏览器会⾃动尝试重新连接(⽀持 retry 字段指定重连间隔)。
⾃定义消息类型
客⼾端发起请求后,服务器保持连接开放,响应头设置 Content-Type: text/event
stream ,标识为事件流格式,持续推送事件流。

相关推荐
有颜有货1 小时前
PMC生产排产的4种算法,一次讲清
java·服务器·前端
智恒百亿1 小时前
算力基建深度分析:国内服务器产业高强度迭代下的技术壁垒与全球化优势
服务器·人工智能·算力基建
fei_sun1 小时前
等价负载均衡(等价路由ECMP)
运维·负载均衡
楷哥爱开发2 小时前
降低网络爬虫成本:基础设施优化指南
服务器·开发语言·php
鱼很腾apoc2 小时前
【Linux】第7期 进程间通信 (IPC) 详解:管道 (匿名 / 命名) + System V
linux·服务器·c语言·学习·进程间通信·ipc
zh73142 小时前
docker日志监控dozzle,高性能,性能消耗小
运维·docker·容器
yxl874646462 小时前
PCTG-1015型Profinet转Ethernet/IP协议转换器
服务器·网络·物联网·网络协议·自动化·信息与通信
weixin_471383032 小时前
Docker - 05 - Railway 部署
运维·docker·容器
你觉得脆皮鸡好吃吗2 小时前
【THM】JWT Security & Protocols and Servers(AI)
运维·服务器·网络