RAG系統構建之嵌入模型性能優化完整指南

導讀:在企業級RAG系統的實際部署中,您是否遇到過這樣的困擾:嵌入計算成本不斷攀升,API調用頻繁觸及限制,而系統響應速度卻始終達不到用戶期望?這些看似分散的問題,實際上都指向同一個技術核心:嵌入模型的性能優化。
本文深入解析CacheBackedEmbeddings緩存機制的技術原理與實戰應用,從理論基礎到生產環境部署,為您提供完整的優化解決方案。通過合理的緩存策略,典型企業知識庫可實現70-80%的API調用減少,響應速度提升10-100倍,這背后的技術機制值得每一位RAG系統開發者深入了解。
文章涵蓋核心痛點分析、技術架構深度解析、生產環境實戰案例,以及從本地文件存儲到Redis集群的完整存儲方案對比。特別針對智能客服知識庫優化實戰,詳細展示了從傳統方案到緩存優化的完整演進過程。無論您是初次接觸RAG系統,還是正在尋求性能突破的資深開發者,這份指南都將為您的技術實踐提供有價值的參考。

前言

在當今大模型時代,RAG(Retrieval-Augmented Generation)系統已成為企業級AI應用的核心基礎設施。然而,嵌入模型的性能優化往往是決定整個系統成敗的關鍵環節。本文將從理論基礎到實戰應用,全面解析嵌入模型性能優化的核心策略,特別是CacheBackedEmbeddings緩存機制的深度應用。

該文章繼嵌入大模型詳解,文章直通車:嵌入大模型與LLM技術全面解析與實戰指南

第一部分:需求背景與核心痛點分析

RAG系統中的嵌入計算挑戰

在RAG系統的實際部署過程中,嵌入計算環節面臨著多重技術挑戰,這些問題直接影響著系統的整體性能和商業可行性。

成本控制的嚴峻現實

嵌入生成的計算成本往往被低估。以OpenAI的text-embedding-ada-002為例,處理1000個token的費用約為0.0001美元。看似微不足道的單價,在面對大規模文檔處理時會迅速累積成顯著的運營成本。一個包含100萬文檔的企業知識庫,僅初始嵌入生成就可能產生數千美元的費用。

重復計算的資源浪費

更為嚴重的問題在于重復計算。在實際應用中,相同的文檔段落、標準化的產品描述、重復的FAQ內容會被多次處理。據統計,典型的企業知識庫中約有30-40%的內容存在不同程度的重復,這意味著超過三分之一的嵌入計算實際上是不必要的資源消耗。

API限制與響應延遲

商業嵌入服務的調用限制構成了另一層約束。以Azure OpenAI服務為例,標準版本每分鐘最多支持3000次調用。在高并發場景下,這一限制很容易成為系統瓶頸。同時,每次實時調用API的網絡延遲(通常在100-500ms之間)在用戶體驗方面也難以接受。

緩存機制的技術價值

面對上述挑戰,緩存機制提供了一條經濟高效的解決路徑。通過合理的緩存策略,我們能夠實現以下核心價值:

顯著的成本降低效應

緩存機制的投資回報率通常非常可觀。以一個中等規模的知識庫為例,通過緩存策略可以減少70-80%的重復API調用。按照前文的成本估算,這意味著數千美元的直接成本節約,投資回報周期往往在數周內就能實現。

性能提升的量級差異

從性能角度來看,緩存讀取與API調用之間存在著量級差異。本地文件系統的緩存讀取通常在10-50ms內完成,而Redis等內存緩存的訪問時間更是可以控制在1-5ms。相比之下,API調用的總耗時(包括網絡傳輸和模型計算)往往需要200-1000ms,性能提升可達10-100倍。

第二部分:CacheBackedEmbeddings技術深度解析

核心架構設計原理

CacheBackedEmbeddings采用了經典的緩存代理模式(Cache Proxy Pattern),這一設計模式在分布式系統中被廣泛應用。其核心工作流程如下:

用戶請求 → 緩存鍵生成 → 緩存查詢 → 命中判斷↓命中 → 直接返回緩存結果↓未命中 → 調用底層模型 → 計算嵌入 → 存儲到緩存 → 返回結果

這一架構的精妙之處在于其透明性:對于調用方而言,帶緩存的嵌入模型與原生模型具有完全相同的接口,實現了緩存邏輯的完全封裝。

哈希算法與緩存鍵設計

系統采用SHA-256哈希算法對輸入文本進行處理,生成唯一的緩存鍵。這一設計確保了即使是微小的文本差異也會產生完全不同的緩存鍵,避免了緩存沖突的可能性。同時,哈希算法的單向性也保證了緩存系統的安全性。

API設計哲學的深度思考

LangChain框架在API設計上體現了深刻的工程哲學,特別是對embed_documentsembed_query兩個方法的差異化處理。

embed_documents方法的設計考量

embed_documents方法專門針對批量文檔處理場景進行了優化。在知識庫構建、文檔預處理等場景中,大量文檔具有相似的結構和內容,緩存命中率較高。更重要的是,這類場景通常可以容忍較長的處理時間,因此緩存的讀寫開銷可以被攤薄。

embed_query方法的設計哲學

相比之下,embed_query方法的設計更加注重實時性。用戶查詢的多樣性決定了緩存命中率相對較低,而實時查詢場景對響應時間的敏感性又要求系統避免不必要的開銷。因此,該方法默認不啟用緩存機制,體現了"針對場景優化"的設計理念。

核心實現語法詳解

CacheBackedEmbeddings的基礎實現語法簡潔而強大:

from langchain.embeddings import CacheBackedEmbeddings
from langchain.storage import LocalFileStore# 基礎配置
cache_store = LocalFileStore("./embedding_cache/")
cached_embeddings = CacheBackedEmbeddings.from_bytes_store(underlying_embeddings=base_model,    # 底層嵌入模型document_embedding_store=cache_store, # 緩存存儲實現namespace="production_v1"            # 版本命名空間
)

參數配置的最佳實踐

  • underlying_embeddings:支持任何符合LangChain標準的嵌入模型
  • document_embedding_store:提供了豐富的存儲選項,從本地文件到分布式緩存
  • namespace:版本控制的關鍵,建議采用"項目名_模型版本_日期"的命名規范

存儲方案的技術選型

LangChain提供了完整的存儲生態系統,每種方案都有其特定的適用場景:

# 本地文件存儲 - 適合開發和小規模部署
from langchain.storage import LocalFileStore
local_store = LocalFileStore("./cache")# Redis存儲 - 適合生產環境和分布式部署
from langchain.storage import RedisStore
from redis import Redis
redis_client = Redis(host="localhost", port=6379)
redis_store = RedisStore(redis_client, ttl=86400)# 內存存儲 - 適合臨時測試和高性能場景
from langchain.storage import InMemoryStore
memory_store = InMemoryStore()

第三部分:生產環境實戰案例分析

智能客服知識庫優化實戰

以一個典型的智能客服系統為例,該系統需要處理包含10萬條問答對的企業知識庫。在傳統實現方式下,每次用戶提問都需要重新計算所有相關問題的嵌入,這種方式在性能和成本方面都存在顯著問題。

傳統方案的性能瓶頸

在未使用緩存的情況下,系統的響應時間分析如下:

  • 嵌入計算:800-1200ms(取決于文本長度和API響應速度)
  • 向量檢索:50-100ms(使用FAISS或類似向量數據庫)
  • 答案生成:300-500ms(大語言模型推理時間)

總響應時間往往超過1.5秒,遠超用戶期望的500ms響應標準。

緩存優化的分階段實施

優化方案采用了分階段的緩存策略:

  1. 預熱階段:系統啟動時對核心知識庫進行批量嵌入計算
  2. 運行階段:用戶查詢直接讀取緩存,避免實時計算
  3. 更新階段:知識庫更新時增量維護緩存數據

代碼實現的完整演示

基礎版本實現(無緩存)

from langchain.embeddings import OpenAIEmbeddings
import time# 基礎嵌入模型初始化
base_embedder = OpenAIEmbeddings(openai_api_key="your-api-key",model="text-embedding-ada-002"
)# 模擬知識庫查詢場景
def search_knowledge_base(query, knowledge_base):start_time = time.time()# 為查詢生成嵌入query_embedding = base_embedder.embed_query(query)# 為知識庫文檔生成嵌入(每次都重新計算)doc_embeddings = base_embedder.embed_documents(knowledge_base)# 計算相似度并返回最佳匹配# ... 相似度計算邏輯 ...end_time = time.time()print(f"查詢耗時: {end_time - start_time:.3f}秒")return best_match

優化版本實現(帶緩存)

from langchain.embeddings import CacheBackedEmbeddings
from langchain.storage import LocalFileStore
import time# 創建緩存存儲
cache_store = LocalFileStore("./embeddings_cache/")# 初始化帶緩存的嵌入器
cached_embedder = CacheBackedEmbeddings.from_bytes_store(underlying_embeddings=base_embedder,document_embedding_store=cache_store,namespace="customer_service_v2"
)def optimized_search_knowledge_base(query, knowledge_base):start_time = time.time()# 查詢嵌入(通常不使用緩存,因為查詢多樣性高)query_embedding = cached_embedder.embed_query(query)# 知識庫嵌入(從緩存讀取,顯著提升性能)doc_embeddings = cached_embedder.embed_documents(knowledge_base)# 相似度計算和匹配邏輯# ... 相似度計算邏輯 ...end_time = time.time()print(f"優化后查詢耗時: {end_time - start_time:.3f}秒")return best_match

性能對比與效果驗證

通過實際測試,我們來驗證緩存機制的性能提升效果:

# 性能測試代碼
import time# 準備測試數據(模擬重復文檔)
test_documents = ["如何重置賬戶密碼?","賬戶被鎖定了怎么辦?","如何修改個人信息?","如何重置賬戶密碼?",  # 重復文檔"忘記用戶名怎么找回?","賬戶被鎖定了怎么辦?"   # 重復文檔
]# 首次調用測試(建立緩存)
print("=== 首次調用測試 ===")
start_time = time.time()
embeddings_first = cached_embedder.embed_documents(test_documents)
first_call_time = time.time() - start_time
print(f"首次調用耗時: {first_call_time:.3f}秒")
print(f"生成嵌入數量: {len(embeddings_first)}")
print(f"嵌入維度: {len(embeddings_first[0])}")# 二次調用測試(使用緩存)
print("\n=== 二次調用測試 ===")
start_time = time.time()
embeddings_second = cached_embedder.embed_documents(test_documents)
second_call_time = time.time() - start_time
print(f"二次調用耗時: {second_call_time:.3f}秒")
print(f"結果一致性驗證: {embeddings_first == embeddings_second}")# 性能提升計算
if second_call_time > 0:speedup_ratio = first_call_time / second_call_timeprint(f"\n性能提升倍數: {speedup_ratio:.1f}x")print(f"時間節省比例: {((first_call_time - second_call_time) / first_call_time * 100):.1f}%")

第四部分:高級配置與生產環境部署

分布式Redis緩存配置

對于需要支持多實例部署和高可用性的生產環境,Redis緩存是最佳選擇:

from redis import Redis
from langchain.storage import RedisStore
import jsonclass AdvancedRedisStore(RedisStore):"""增強版Redis存儲,支持更多企業級特性"""def __init__(self, redis_client, ttl=None, key_prefix="emb:"):super().__init__(redis_client, ttl)self.key_prefix = key_prefixdef get_cache_stats(self):"""獲取緩存統計信息"""info = self.redis_client.info('memory')keys_count = self.redis_client.dbsize()return {'total_keys': keys_count,'memory_usage': info.get('used_memory_human', 'N/A'),'hit_rate': self._calculate_hit_rate()}def _calculate_hit_rate(self):"""計算緩存命中率"""# 實現緩存命中率計算邏輯pass# Redis集群配置
redis_client = Redis(host="redis-cluster.your-domain.com",port=6379,password="your-redis-password",db=0,socket_connect_timeout=5,socket_timeout=5,retry_on_timeout=True,health_check_interval=30
)# 創建增強版Redis緩存
redis_store = AdvancedRedisStore(redis_client=redis_client,ttl=7 * 24 * 3600,  # 7天過期時間key_prefix="prod_embeddings:"
)# 生產環境嵌入器配置
production_embedder = CacheBackedEmbeddings.from_bytes_store(underlying_embeddings=base_embedder,document_embedding_store=redis_store,namespace=f"prod_{model_version}_{deployment_date}"
)

緩存策略的精細化管理

在生產環境中,緩存策略需要考慮更多的業務場景和技術約束:

class SmartCacheManager:"""智能緩存管理器"""def __init__(self, cached_embedder, cache_store):self.cached_embedder = cached_embedderself.cache_store = cache_storeself.hit_count = 0self.miss_count = 0def embed_with_monitoring(self, texts):"""帶監控的嵌入計算"""start_time = time.time()# 檢查緩存命中情況cache_hits = self._check_cache_hits(texts)# 執行嵌入計算embeddings = self.cached_embedder.embed_documents(texts)# 更新統計信息self._update_stats(cache_hits, len(texts))execution_time = time.time() - start_time# 記錄性能指標self._log_performance_metrics(len(texts), execution_time, cache_hits)return embeddingsdef _check_cache_hits(self, texts):"""檢查緩存命中情況"""# 實現緩存預檢查邏輯passdef _update_stats(self, cache_hits, total_count):"""更新統計信息"""self.hit_count += cache_hitsself.miss_count += (total_count - cache_hits)def _log_performance_metrics(self, text_count, execution_time, cache_hits):"""記錄性能指標"""hit_rate = cache_hits / text_count if text_count > 0 else 0avg_time_per_text = execution_time / text_count if text_count > 0 else 0print(f"批次處理完成:")print(f"  - 文本數量: {text_count}")print(f"  - 緩存命中率: {hit_rate:.2%}")print(f"  - 平均處理時間: {avg_time_per_text:.3f}秒/文本")print(f"  - 總執行時間: {execution_time:.3f}秒")def get_overall_stats(self):"""獲取整體統計信息"""total_requests = self.hit_count + self.miss_countoverall_hit_rate = self.hit_count / total_requests if total_requests > 0 else 0return {'total_requests': total_requests,'cache_hits': self.hit_count,'cache_misses': self.miss_count,'hit_rate': overall_hit_rate}

第五部分:最佳實踐與性能調優指南

適用場景的深度分析

CacheBackedEmbeddings機制在不同場景下的適用性存在顯著差異,理解這些差異對于系統設計至關重要。

高價值場景識別

  1. 標準化內容處理:法律文檔、合規條款、產品規格說明等具有高度標準化特征的內容,重復率往往超過60%,緩存價值極高。

  2. 批量文檔預處理:知識庫構建、文檔索引生成等離線處理場景,可以充分利用緩存的時間攤薄效應。

  3. 版本化內容管理:當內容更新頻率較低(如月度或季度更新)時,緩存的長期價值得以充分體現。

需要謹慎評估的場景

  1. 高頻變化內容:新聞資訊、社交媒體內容等更新頻繁的場景,緩存命中率較低。

  2. 個性化查詢:用戶生成的查詢內容具有高度個性化特征,緩存效果有限。

  3. 實時性要求極高的場景:某些場景下,緩存的讀寫開銷可能超過直接計算的成本。

存儲方案的深度對比

存儲方案性能特征運維復雜度成本考量適用規模
LocalFileStore讀寫:10-50ms極低僅存儲成本單機應用
RedisStore讀寫:1-5ms中等Redis運維成本中大型集群
InMemoryStore讀寫:<1ms內存成本較高高性能場景
UpstashRedis讀寫:5-20ms極低按使用量計費云原生應用

性能監控與調優策略

建立完善的性能監控體系是生產環境部署的關鍵:

class PerformanceMonitor:"""性能監控組件"""def __init__(self):self.metrics = {'total_requests': 0,'cache_hits': 0,'avg_response_time': 0,'error_count': 0}def record_request(self, hit_status, response_time, error=None):"""記錄請求指標"""self.metrics['total_requests'] += 1if hit_status:self.metrics['cache_hits'] += 1# 更新平均響應時間current_avg = self.metrics['avg_response_time'] n = self.metrics['total_requests']self.metrics['avg_response_time'] = (current_avg * (n-1) + response_time) / nif error:self.metrics['error_count'] += 1def generate_report(self):"""生成性能報告"""hit_rate = self.metrics['cache_hits'] / max(self.metrics['total_requests'], 1)report = f"""=== 緩存性能報告 ===總請求數: {self.metrics['total_requests']}緩存命中率: {hit_rate:.2%}平均響應時間: {self.metrics['avg_response_time']:.3f}秒錯誤數量: {self.metrics['error_count']}系統穩定性: {(1 - self.metrics['error_count']/max(self.metrics['total_requests'], 1)):.2%}"""return report

故障恢復與容錯機制

生產環境中的容錯設計同樣重要:

class RobustCachedEmbeddings:"""帶容錯機制的緩存嵌入器"""def __init__(self, base_embedder, cache_store, fallback_mode=True):self.base_embedder = base_embedderself.cache_store = cache_storeself.fallback_mode = fallback_modeself.cached_embedder = CacheBackedEmbeddings.from_bytes_store(base_embedder, cache_store)def embed_documents_safe(self, texts, retry_count=3):"""安全的嵌入計算,包含重試和降級機制"""for attempt in range(retry_count):try:return self.cached_embedder.embed_documents(texts)except Exception as e:print(f"緩存嵌入失敗 (嘗試 {attempt + 1}/{retry_count}): {str(e)}")if attempt == retry_count - 1:  # 最后一次嘗試if self.fallback_mode:print("啟用降級模式,直接調用基礎模型")return self.base_embedder.embed_documents(texts)else:raise etime.sleep(2 ** attempt)  # 指數退避return None

總結與展望

通過本文的深入分析,我們可以看到CacheBackedEmbeddings不僅僅是一個簡單的緩存工具,而是一個完整的嵌入計算優化解決方案。它通過巧妙的架構設計和豐富的配置選項,為不同規模和需求的RAG系統提供了靈活而強大的性能優化能力。

核心價值總結

  1. 成本效益顯著:在典型應用場景下,可實現70-80%的API調用減少,直接轉化為成本節約。

  2. 性能提升明顯:10-100倍的響應速度提升,顯著改善用戶體驗。

  3. 架構設計優雅:透明的代理模式設計,無需修改現有代碼即可獲得緩存能力。

  4. 生產環境就緒:完善的存儲選項和容錯機制,滿足企業級部署需求。

未來發展方向

隨著大模型技術的不斷發展,嵌入模型的緩存優化也將面臨新的機遇和挑戰。可以預見的發展方向包括:

  • 智能緩存策略:基于機器學習的緩存命中率預測和動態調整
  • 分層緩存架構:結合本地緩存和分布式緩存的混合方案
  • 語義相似性緩存:不僅緩存完全匹配的文本,還能利用語義相似的緩存結果

掌握CacheBackedEmbeddings的核心原理和最佳實踐,將為構建高效、可靠的RAG系統奠定堅實的技術基礎。在實際應用中,建議根據具體的業務場景、技術架構和性能要求,選擇最適合的緩存配置方案,并建立完善的監控和運維體系,確保系統的長期穩定運行。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/907285.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/907285.shtml
英文地址,請注明出處:http://en.pswp.cn/news/907285.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

python 自動生成不同行高的word

python 自動生成不同行高的word # -*- coding: utf-8 -*- from docx import Document from docx.shared import Cm, Pt, Inches from docx.oxml import OxmlElement from docx.oxml.ns import qn from docx.enum.text import WD_ALIGN_PARAGRAPHclass DynamicTableGenerator:d…

如何訓練意志力

設定清晰的目標 目標需要是具體的&#xff0c;可實現的&#xff0c;有時間限制的。比如不要說“我要鍛煉”&#xff0c;而是改成“每周跑步3次&#xff0c;每次30分鐘”。 從小事開始 起步通常都是困難的&#xff0c;一開始定一個很大很復雜的任務也超出了自己的能力&#x…

FastAPI 依賴注入

依賴注入常用于以下場景&#xff1a; 共享業務邏輯&#xff08;復用相同的代碼邏輯&#xff09; 共享數據庫連接 實現安全、驗證、角色權限 等…… 上述場景均可以使用依賴注入&#xff0c;將代碼重復最小化。 創建依賴項 依賴項就是一個函數&#xff0c;且可以使用與路…

接口冪等性原理與方案總結

文章目錄 接口冪等概念典型場景核心解決方案一鎖二判三更新 方案選型對比 接口冪等概念 定義&#xff1a;無論調用接口多少次&#xff0c;對系統的影響與單次調用一樣 范疇&#xff1a;在后端開發中&#xff0c;通常更關注寫接口的冪等&#xff0c;因為寫接口才會對系統數據造…

【已解決】windows gitbash 出現CondaError: Run ‘conda init‘ before ‘conda activate‘

在 Git Bash 中執行&#xff1a; source /c/Users/你的用戶名/miniconda3/etc/profile.d/conda.sh # 注意填入你自己的路徑 conda init bash關閉并重新打開 Git Bash 終端。測試激活環境&#xff1a; conda activate your_env_name注意事項 要把上述命令中的 你的用戶名 替…

軟件包管理系統的架構與生態機制

文章目錄 前言一、總結二、如何上傳自己的軟件包 前言 在日常軟件開發中&#xff0c;我們經常使用諸如apt install, pip install, npm install之類的命令&#xff0c;但有一個問題是&#xff0c;這些下載命令是從哪里下載的這些軟件包&#xff0c;以及我們是否能上傳自己的代碼…

Java線程池管理最佳實踐(設計模式)

引言 在多線程編程中&#xff0c;線程池是一種非常重要的資源管理工具。合理使用線程池可以顯著提高系統性能&#xff0c;避免頻繁創建和銷毀線程帶來的開銷。今天&#xff0c;我將為大家深入分析一個實用的ThreadPoolManager實現&#xff0c;它來自com.kingdee.eas.util包&am…

4.8.2 利用Spark SQL計算總分與平均分

在本次實戰中&#xff0c;我們的目標是利用Spark SQL計算學生的總分與平均分。首先&#xff0c;我們準備了包含學生成績的數據文件&#xff0c;并將其上傳至HDFS。接著&#xff0c;通過Spark的交互式編程環境&#xff0c;我們讀取了成績文件并將其轉換為結構化的DataFrame。然后…

HTML 文件路徑完全指南:相對路徑、絕對路徑解析與引用技巧

一、為什么必須學會文件路徑&#xff1f;—— 網頁引用資源的 “地址規則” 在 HTML 中&#xff0c;引用圖片、CSS、JS 等外部文件時&#xff0c;必須通過文件路徑告訴瀏覽器資源的位置。路徑錯誤會導致資源無法加載&#xff08;頁面出現 broken image 圖標或樣式丟失&#xf…

keepalived兩臺設備同時出現VIP問題

目錄 問題背景&#xff1a; 日志分析如下&#xff1a; 原因和解決方案總結&#xff1a; 問題背景&#xff1a; keepalived-master和keepalived-slave同時出現了VIP&#xff0c;出現了非對稱路由和雙主現象 日志分析如下&#xff1a; master能夠接受到來自slave的通告消息…

【開源解析】基于PyQt5+Folium的谷歌地圖應用開發:從入門到實戰

&#x1f310;【開源解析】基于PyQt5Folium的谷歌地圖應用開發&#xff1a;從入門到實戰 &#x1f308; 個人主頁&#xff1a;創客白澤 - CSDN博客 &#x1f525; 系列專欄&#xff1a;&#x1f40d;《Python開源項目實戰》 &#x1f4a1; 熱愛不止于代碼&#xff0c;熱情源自每…

篇章五 數據結構——鏈表(一)

目錄 1.ArrayList的缺陷 2. 鏈表 2.1 鏈表的概念及結構 2.2 鏈表結構 1. 單向或者雙向 2.帶頭或者不帶頭 3.循環或者非循環 2.3 鏈表的實現 1.完整代碼 2.圖解 3.顯示方法 4.鏈表大小 5. 鏈表是否存在 key 值 6.頭插法 7.尾插法 8.中間插入 9.刪除key值節點 10.…

數據庫相關面試

數據庫相關面試 Mysql MySQL中的事務隔離級別及其特點 參考&#xff1a;事務的隔離級別&#xff1a;可重復讀 未提交讀(Read Uncommitted)&#xff1a;允許臟讀&#xff0c;也就是可能讀取到其他會話中未提交事務修改的數據 已提交讀(Read Committed)&#xff1a;只能讀取到…

基于Scrapy的天貓商品數據爬取與分析實戰(含API簽名破解與可視化)

基于Scrapy的天貓商品數據爬取與分析實戰&#xff08;含API簽名破解與可視化&#xff09; 本文以華為Mate 60 Pro為例&#xff0c;詳細介紹如何使用Scrapy框架爬取天貓商品數據&#xff0c;涵蓋API簽名破解、反爬應對、數據存儲及可視化全流程&#xff0c;適合爬蟲進階學習者實…

【C++進階篇】哈希表的模擬實現(賦源碼)

這里寫目錄標題 前言一. 開放地址法實現哈希表1.1 閉散列結構定義1.2 構造函數1.3 插入&#xff08;線性探測&#xff09;1.3.1 傳統寫法1.3.2 現代寫法 1.4 查找1.5 刪除 二. 鏈地址法實現哈希表&#xff08;哈希桶&#xff09;2.1 開散列結構定義2.2 構造函數2.3 插入2.4 查找…

07-后端Web實戰(部門管理)

5. 修改部門 對于任何業務的修改功能來說&#xff0c;一般都會分為兩步進行&#xff1a;查詢回顯、修改數據。 5.1 查詢回顯 5.1.1 需求 當我們點擊 "編輯" 的時候&#xff0c;需要根據ID查詢部門數據&#xff0c;然后用于頁面回顯展示。 5.1.2 接口描述 參照參照…

深度解析項目集方向或目標根本性轉變的應對策略 —— 項目集管理實戰指南

在復雜多變的商業環境中&#xff0c;項目集管理面臨著重重挑戰&#xff0c;而項目集方向或目標的根本性轉變無疑是其中最具沖擊力的問題之一。本文將深度剖析這一難題&#xff0c;為項目集管理從業者提供實用、新穎且富有價值的應對策略&#xff0c;助力大家在項目集管理的復雜…

JAVA面試復習知識點

面試中遇到的題目&#xff0c;記錄復習&#xff08;持續更新&#xff09; Java基礎 1.String的最大長度 https://www.cnblogs.com/wupeixuan/p/12187756.html 2.集合 Collection接口的實現&#xff1a; List接口&#xff1a;ArraryList、LinkedList、Vector Set接口&#xff1a…

【燒腦算法】定長滑動窗口:算法題中的“窗口”智慧

目錄 引言 定長滑動窗口習題剖析 3439. 重新安排會議得到最多空余時間 I 2134. 最少交換次數來組合所有的 1 II 1297. 子串的最大出現次數 2653. 滑動子數組的美麗值 567. 字符串的排列 438. 找到字符串中所有字母異位詞 30. 串聯所有單詞的子串 220. 存在重復元素 II…

JWT安全:接收無簽名令牌.【簽名算法設置為none繞過驗證】

JWT安全&#xff1a;假密鑰【簽名隨便寫實現越權繞過.】 JSON Web 令牌 (JWT)是一種在系統之間發送加密簽名 JSON 數據的標準化格式。理論上&#xff0c;它們可以包含任何類型的數據&#xff0c;但最常用于在身份驗證、會話處理和訪問控制機制中發送有關用戶的信息(“聲明”)。…