01
배경 소개
대규모 언어 모델의 효과가 눈에 띄게 향상됨에 따라 관련 응용 프로그램이 지속적으로 등장하고 점점 더 대중적인 추세를 보이고 있습니다. 가장 널리 관심을 끄는 기술 경로 중 하나는 LLM(대형 언어 모델) + 지식 회상(Knowledge Retrieval) 방법으로, 이는 개인 도메인 지식 질문 답변 측면에서 일반 대형 언어 모델의 일부 단점을 보완하고 문제를 해결할 수 있습니다. 일반적인 대형 언어 모델의 문제 언어 모델은 전문 분야의 기초 부족, 환각 및 기타 질문에 답합니다. 기본 아이디어는 개인 도메인 지식 문서를 분할한 다음 이를 벡터화하고 벡터 검색을 통해 회상한 다음 이를 유도 및 요약을 위해 대규모 언어 모델에 컨텍스트로 입력하는 것입니다.
본 기술방향의 구체적인 실천에서는 지식 질의 응답 과정에서 지식 회상 단계에서 핵심적인 역할을 하는 역산(Inversion)과 벡터(Vector) 기반의 두 가지 인덱스 방식과 일반 문서 인덱스 또는 로그 인덱스를 이용하여 지식 베이스를 구축할 수 있다. , 지식의 벡터화에는 심층 모델의 의미론적 기능, 문서 분할, 벡터 모델 배포 및 추론과 같은 추가 단계가 필요합니다. 지식 벡터화 데이터베이스 구축 과정에서는 원본 문서의 크기뿐만 아니라 분할 세분성, 벡터 차원 및 기타 요소도 고려해야 하며, 결국 벡터 데이터베이스에 의해 색인된 지식 항목의 수는 에 도달할 수 있습니다. 매우 큰 크기는 다음 두 가지 측면으로 인해 결정될 수 있습니다.
금융, 의학, 법률 분야 등 다양한 산업 분야에서는 기존 문서의 양이 매우 많고, 신규 문서의 양도 많습니다.
회상 효과를 추구하기 위해 문서 분할에서는 문장 또는 세그먼트별로 다중 입도 중복 저장을 채택하는 경우가 많습니다.
이러한 세부 사항은 지식 벡터 데이터베이스의 작성 및 쿼리 성능에 특정 문제를 가져옵니다. 벡터화된 지식 베이스의 구축 및 관리를 최적화하기 위해 본 논문에서는 다음 그림과 같은 지식 베이스 구축 프로세스를 구축합니다. 아마존 클라우드 기술:
S3 버킷의 핸들러를 통해 실시간으로 Amazon Lambda를 트리거하여 해당 지식 파일 스토리지에 대한 Amazon Glue 작업을 시작합니다.
문서 구문 분석 및 분할은 Glue 작업에서 수행되며 Amazon Sagemaker의 임베딩 모델은 벡터화를 위해 호출됩니다.
대량을 통해 Amazon OpenSearch에 삽입합니다.
또한 지식을 벡터화하고 벡터 데이터베이스를 최적화하는 방법을 포함하여 전체 프로세스와 관련된 다양한 측면에 대한 몇 가지 모범 사례와 경험을 요약합니다.
02
지식 벡터화
2.1 문서 분할
지식 벡터화의 전단계는 지식을 분할하는 것이며, 의미적 무결성을 유지하는 것이 가장 중요한 고려사항이다. 두 가지 측면에서 논의합니다. 다음 두 가지 초점을 선택하는 방법은 각각 몇 가지 경험을 요약했습니다.
가. 단편을 분할하는 방법
이 작업 부분과 관련하여 널리 사용되는 대규모 언어 모델 통합 프레임워크인 Langchain은 많은 문서 로더 및 텍스트 스필터를 제공하며 그 중 일부는 참조 가치가 있지만 대부분은 반복적입니다.
현재 가장 많이 사용되는 기본 방법은 Langchain의 기본 Splitter인 RecursiveCharacterTextSplitter를 Langchain에서 사용하는 것입니다. 이 다중 레벨로 구분된 문자 목록(["\n\n", "\n", " ", ""])을 사용하여 분할합니다. 기본적으로 먼저 단락에 따라 분할됩니다. 분할 결과의 Chunk_size가 다음을 초과하는 경우 그런 다음 계속해서 다음 수준의 구분 기호 문자를 사용하여 Chunk_size 요구 사항이 충족될 때까지 분할을 계속합니다.
그러나 이 접근 방식은 상대적으로 거칠며 일부 핵심 콘텐츠가 분해될 수 있습니다. 일부 다른 문서 형식의 경우 좀 더 미묘한 관행이 있을 수 있습니다.
FAQ 파일은 하나의 질문과 하나의 답변의 세분성에 따라 분할되어야 합니다. 후속 벡터화된 입력은 질문 또는 질문 + 답변만 사용할 수 있습니다. (자세한 내용은 이 블로그 시리즈의 후속 기사에서 논의)
Markdown 파일의 경우 "#"은 제목을 식별하는 데 사용되는 특수 문자입니다. MarkdownHeaderTextSplitter를 분할자로 사용할 수 있어 콘텐츠와 제목이 그에 따라 추출되도록 더 잘 보장할 수 있습니다.
PDF 파일에는 더 풍부한 형식 정보가 포함됩니다. Langchain은 많은 로더를 제공하지만 Langchain의 PDFMinerPDFasHTMLLoader의 분할 효과가 더 좋을 것입니다.PDF를 HTML로 변환하고 HTML <div> 블록으로 분할합니다.이 방법을 사용하면 각 블록의 내용을 보존할 수 있습니다.글꼴 크기 정보를 각 콘텐츠의 관련 관계를 추론할 수 있으며, 단락의 제목을 이전 수준의 상위 제목과 연결하여 정보를 더욱 완전하게 만들 수 있습니다. 아래 효과와 유사합니다.
b. 조각 길이에 대한 모델 지원
분할 조각은 벡터화된 모델을 통해 추론해야 하므로 벡터화된 모델의 Max_seq_length 제한을 고려해야 하며, 이 제한을 초과하면 잘림 및 불완전한 의미가 발생할 수 있습니다. 지원되는 Max_seq_length를 기준으로 아래 표와 같이 현재 두 가지 유형의 Embedding 모델이 있습니다. (이 네 가지는 실제 경험이 있는 모델입니다.)
여기서 Max_seq_length는 토큰 수를 나타내며 문자 수와 동일하지 않습니다. 이전 테스트 경험에 따르면 처음 3개 모델의 토큰은 한자 1.5자 정도였다. chatglm과 같은 대규모 언어 모델의 경우 토큰은 일반적으로 약 2자입니다. 분할 시 토큰 개수를 계산하는 것이 불편한 경우 이 비율에 따라 간단히 변환하면 잘림 현상이 발생하지 않습니다.
처음 세 가지 모델은 Bert 기반 Embedding 모델에 속하며 OpenAI의 text-embedding-ada-002 모델은 GPT3 기반 모델입니다. 전자는 문장이나 짧은 문단의 벡터화에 적합하고, 후자는 OpenAI의 SAAS 인터페이스로 긴 텍스트의 벡터화에 적합하지만 비공개적으로 배포할 수는 없습니다.
회상 효과를 기반으로 검증 선택을 할 수 있습니다. 현재의 실제 경험으로 볼 때 text-embedding-ada-002는 중국어 유사성 점수를 매길 수 있지만 차별 정도가 충분하지 않아(집중도는 약 0.7) 유사 여부를 직접적으로 판단하는 데 도움이 되지 않음을 알 수 있습니다. 임계값을 통한 지식 회상.
또한, 길이 제한 문제를 개선할 수 있는 또 다른 방법이 있는데, 분할된 조각에 번호를 매길 수 있고, 인접한 조각의 수도 가깝습니다. 조각 중 하나를 불러올 때 벡터 데이터베이스의 범위 검색을 사용하여 다음을 수행할 수 있습니다. 근처의 조각을 검색합니다. 회상은 또한 회상된 콘텐츠의 의미적 무결성을 보장할 수 있습니다.
2.2 벡터화된 모델 선택
이전 섹션에서 언급한 4개 모델은 모델의 텍스트 길이 지원 차이만 언급했을 뿐 현재 그 효과에 대한 그다지 권위 있는 결론은 없습니다. 리더보드를 사용하여 각 모델의 성능을 이해할 수 있습니다. 목록에 있는 대부분의 모델에 대한 평가는 여전히 공개 데이터 세트의 벤치마크를 기반으로 합니다. 벤치마크 결론이 실제 생산 현장에서 사실인지 여부는 확인해야 합니다. 사례별로. 그러나 원칙적으로 공유할 수 있는 경험의 측면은 다음과 같습니다.
수직 필드의 Finetune 모델은 원래 벡터 모델에 비해 분명한 이점을 가지고 있습니다.
현재 벡터화된 모델은 대칭형과 비대칭형의 두 가지 범주로 분류됩니다. 미세 조정 없이 FAQ에 대해서는 대칭적 회상, 즉 Query to Question을 사용하는 것이 좋습니다. 문서 조각 지식의 경우 쿼리에서 답변까지의 회상(문서 조각)인 비대칭 회상 모델을 사용하는 것이 좋습니다.
효과에 뚜렷한 차이가 없다면 벡터 차원이 짧은 모델을 선택해 보세요. 고차원 벡터(예: openai의 text-embedding-ada-002)는 검색 성능과 비용 측면에서 벡터 데이터베이스에 부담을 줄 것입니다.
이 시리즈의 회상 최적화 부분에서 더 자세히 논의할 것입니다.
2.3 벡터화된 병렬성
실제 비즈니스 시나리오에서 문서 크기는 1억에서 100만 정도입니다. 중복다단계 회상법에 따르면, 해당 지식항목의 규모는 최대 1억개에 달할 수 있다. 전체 오프라인 계산의 규모가 크기 때문에 동시에 수행해야 합니다. 그렇지 않으면 지식 추가 및 벡터 검색 효과 반복 요구 사항을 충족할 수 없습니다. 단계는 주로 다음 세 가지 계산 단계로 구분됩니다.
문서 분할 병렬
계산의 동시성 세분성은 파일 수준에 있으며 처리되는 파일 형식도 TXT 일반 텍스트, 마크다운, PDF 등 다양하며 해당 분할 논리도 다릅니다. 병렬 처리를 위해 Spark와 같은 빅데이터 프레임워크를 사용하는 것은 적절하지 않습니다. 다중 프로세스 동시 처리를 위해 다중 코어 인스턴스를 사용하는 것은 너무 원시적이며 작업을 관찰하고 추적하는 것이 편리하지 않습니다. 따라서 처리를 위해 Amazon Glue의 Python 셸 엔진을 선택할 수 있습니다. 주요 이점은 다음과 같습니다.
파일 세분성에 따라 동시성을 수행하는 것이 편리하며 동시성 정도가 간단하고 제어 가능합니다. 재시도, 시간 초과 등의 메커니즘을 통해 작업을 추적하고 관찰하는 것이 편리하며, 로그는 Amazon CloudWatch에 직접 연결됩니다.
종속 패키지를 빌드하고 실행하는 것이 편리합니다. –additional-python-modules 매개변수만 지정하면 Glue Python 운영 환경에는 이미 opensearch_py 및 기타 종속성이 함께 제공됩니다.
다음 코드를 참조할 수 있습니다.
glue = boto3.client('glue')
def start_job(glue_client, job_name, bucket, prefix):
response = glue.start_job_run(
JobName=job_name,
Arguments={
'--additional-python-modules': 'pdfminer.six==20221105,gremlinpython==3.6.3,langchain==0.0.162,beautifulsoup4==4.12.2',
'--doc_dir': f'{prefix}',
'--REGION': 'us-west-2',
'--doc_bucket' : f'{bucket}',
'--AOS_ENDPOINT': 'vpc-aos-endpoint',
'--EMB_MODEL_ENDPOINT': 'emb-model-endpoint'
})
return response['JobRunId']
더 보려면 왼쪽으로 스와이프하세요.
참고: 각 Amazon Glue 계정에 대해 동시에 실행되는 기본 최대 작업 수는 200개입니다. 더 많은 수의 동시 작업이 필요한 경우 해당 서비스 할당량 증가를 신청해야 합니다. 백그라운드를 통해 계정 관리자에게 문의할 수 있습니다. .
벡터화된 추론 병렬성
분할된 문단과 문장은 문서 수에 비해 여러 배로 늘어나므로 벡터 모델의 추론 처리량에 따라 전체 프로세스의 처리량이 결정됩니다. 여기서 SageMaker 엔드포인트는 벡터화된 모델을 배포하는 데 사용됩니다. 일반적으로 모델의 처리량 기능을 제공하기 위해 GPU 인스턴스 추론, 다중 노드 엔드포인트/엔드포인트 탄력적 확장성 및 서버 측/클라이언트 측 배치 추론 기능이 있습니다. 이들 중 일부는 효과적인 조치입니다. 오프라인 벡터 지식 기반 구축 현장에서는 다음과 같은 전략을 채택할 수 있습니다.
GPU 인스턴스 배포
벡터화된 모델 CPU 인스턴스는 추론 가능합니다. 그러나 오프라인 시나리오에서는 추론 동시성이 높고 GPU의 처리량은 CPU에 비해 약 20배 증가할 수 있습니다. 따라서 오프라인 시나리오에서는 GPU 추론을 사용할 수 있고, 온라인 시나리오에서는 CPU 추론 전략을 사용할 수 있습니다.
다중 노드 엔드포인트
임시 대규모 동시 벡터 생성의 경우 다중 노드 엔드포인트를 배포하여 처리할 수 있으며 처리 후 종료할 수 있습니다. (참고: 오프라인에서 생성되는 요청량이 갑자기 증가하며 Auto Scaling의 콜드 스타트 시간은 5~6분입니다. 이로 인해 초기 요청이 실수로 표시될 수 있습니다)
클라이언트측 배치를 통한 추론
클라이언트 측 배치 구성은 오프라인 추론에 매우 쉽습니다. 서버 측 배치 추론을 활성화할 필요가 없습니다. 일반적으로 서버 측 배치에는 50ms 또는 100ms와 같은 대기 시간이 있습니다. 추론 지연이 높은 대규모 언어 모델에 더 효과적이지만 벡터화된 추론에는 적합하지 않습니다. 다음 코드를 참조할 수 있습니다.
import hashlib
import itertools
import re
BATCH_SIZE = 30
paragraph_content='sentence1。sentence2。sentence3。sentence4。sentence5。sentence6.'
def sentence_generator(paragraph_content):
sentences = re.split('[。??.!!]', paragraph_content)
for sent in sentences:
yield sent
def batch_generator(generator, batch_size):
while True:
batch = list(itertools.islice(generator, batch_size))
if not batch:
break
yield batch
g = sentence_generator(paragraph_content)
sentence_batches = batch_generator(g, batch_size=BATCH_SIZE)
# iterate batch to infer
for idx, batch in enumerate(sentence_batches):
# client-side batch inference
embeddings = get_embedding(smr_client, batch, endpoint_name)
for sent_id, sent in enumerate(batch):
document = { "publish_date": publish_date, "idx":idx, "doc" : sent, "doc_type" : "Sentence", "content" : paragraph_content, "doc_title": header, "doc_category": "", "embedding" : embeddings[sent_id]}
yield {"_index": index_name, "_source": document, "_id": hashlib.md5(str(document).encode('utf-8')).hexdigest()}
더 보려면 왼쪽으로 스와이프하세요.
OpenSearch 일괄 주입
Amazon OpenSearch의 쓰기 작업은 일괄적으로 일괄적으로 구현할 수 있으며 이는 단일 쓰기에 비해 큰 장점이 있습니다. 다음 코드를 참조하세요:
from opensearchpy import OpenSearch, RequestsHttpConnection,helpers
credentials = boto3.Session().get_credentials()
auth = AWSV4SignerAuth(credentials, region)
client = OpenSearch(
hosts = [{'host': aos_endpoint, 'port': 443}],
http_auth = auth,
use_ssl = True,
verify_certs = True,
connection_class = RequestsHttpConnection
)
gen_aos_record_func = None
if content_type == "faq":
gen_aos_record_func = iterate_QA(file_content, smr_client, index_name, EMB_MODEL_ENDPOINT)
elif content_type in ['txt', 'pdf', 'json']:
gen_aos_record_func = iterate_paragraph(file_content, smr_client, index_name, EMB_MODEL_ENDPOINT)
else:
raise RuntimeError('No Such Content type supported')
response = helpers.bulk(client, gen_aos_record_func)
return response
더 보려면 왼쪽으로 스와이프하세요.
03
벡터 데이터베이스 최적화
벡터 데이터베이스에 대해 선택할 대략적인 검색 알고리즘, 적절한 클러스터 크기 선택 및 클러스터 설정 최적화도 지식 베이스의 읽기 및 쓰기 성능에 중요하며 다음 측면을 고려해야 합니다.
3.1 알고리즘 선택
OpenSearch에서는 HNSW(Hierarchical Navigable Small World)와 IVF(Inverted File)라는 두 가지 k-NN 알고리즘이 제공됩니다.
k-NN 검색 알고리즘을 선택할 때 고려해야 할 몇 가지 요소가 있습니다. 메모리가 제한 요소가 아닌 경우 HNSW 알고리즘을 사용하는 것이 우선적으로 권장됩니다. HNSW 알고리즘은 대기 시간과 재현율을 모두 보장할 수 있기 때문입니다. 메모리 사용량을 제어해야 하는 경우 HNSW와 유사한 쿼리 속도와 품질을 유지하면서 메모리 사용량을 줄이는 IVF 알고리즘을 사용하는 것이 좋습니다. 그러나 메모리가 주요 제한 요소인 경우 HNSW 또는 IVF 알고리즘에 PQ 인코딩을 추가하여 메모리 사용량을 더 줄이는 것이 좋습니다. PQ 인코딩을 추가하면 정확도가 낮아질 수 있다는 점에 유의해야 합니다. 따라서 알고리즘과 최적화 방법을 선택할 때 특정 애플리케이션 요구 사항을 충족하려면 여러 요소를 포괄적으로 고려해야 합니다.
3.2 클러스터 크기 추정
알고리즘을 선택한 후 공식에 따라 필요한 메모리를 계산한 다음 k-NN 클러스터의 크기를 도출할 수 있습니다. HNSW 알고리즘을 예로 들어 보겠습니다.
점유된 메모리 = 1.1 * (4*d + 8*m) * num_Vectors * (number_of_replicas + 1)
그 중 d: 768과 같은 벡터의 차원, m: 제어 레이어의 각 노드 연결 수, num_Vectors: 인덱스의 벡터 문서 수
3.3 배치 주입 최적화
지식 벡터 라이브러리에 많은 양의 데이터를 주입할 때 몇 가지 주요 성능 최적화에 주의를 기울여야 합니다. 다음은 몇 가지 주요 최적화 전략입니다.
새로 고침 간격 비활성화
처음으로 많은 양의 데이터를 수집할 때 더 많은 작은 세그먼트가 생성되는 것을 방지하기 위해 새로 고침 간격을 늘리거나 수집 단계에서 새로 고침 간격(-1로 설정)을 직접 끌 수 있습니다. 데이터 로딩이 완료될 때까지 기다린 후 새로 고침 간격을 다시 활성화합니다.
PUT /my_index/_settings
{
"index": {
"refresh_interval": "-1"
}
}
복제본 비활성화
또한 처음으로 대량의 데이터를 로드할 때 수집 속도를 높이기 위해 복제본을 일시적으로 비활성화할 수 있습니다. 그렇게 하면 데이터 손실의 위험이 발생할 수 있으므로 데이터 로딩이 완료된 후 복제본을 다시 활성화해야 한다는 점에 유의해야 합니다.
PUT /my_index/_settings
{
"index": {
"number_of_replicas": 0
}
}
인덱싱 스레드 늘리기
knn을 처리하는 스레드는 knn.algo_param.index_thread_qty에 의해 지정되며 기본값은 1입니다. 장치에 충분한 CPU 리소스가 있는 경우 이 매개변수를 늘려 k-NN 인덱스 구성 속도를 높일 수 있습니다. 그러나 이는 CPU에 대한 부담을 증가시킬 수 있으므로 먼저 노드의 vcore의 절반을 구성하고 CPU 부하를 관찰하는 것이 좋습니다.
PUT /_cluster/settings
{
"transient": {
"knn.algo_param.index_thread_qty": 8 // c6g.4x的vcore为16, 给到 knn 一半
}
}
더 보려면 왼쪽으로 스와이프하세요.
knn 메모리 비율 증가
knn.memory.circuit_breaker.limit는 메모리 사용량에 관한 파라미터로 기본값은 50%입니다. 필요한 경우 이를 70%로 변경할 수 있습니다. 이 기본값을 예로 들면, 프로그램 주소 지정의 제한으로 인해 시스템에 100GB의 메모리가 있는 경우 일반적으로 JVM에 할당된 최대 힙 메모리는 32GB이고 k-NN 플러그인은 나머지 68GB의 절반을 사용합니다. 즉, k-NN의 인덱스 캐시로 34GB입니다. 메모리 사용량이 이 값을 초과하면 k-NN은 가장 최근에 사용된 벡터를 삭제합니다. 이 매개변수는 클러스터 크기가 변경되지 않은 상태에서 k-NN의 캐시 적중률을 향상시켜 비용을 절감하고 검색 효율성을 높이는 데 도움이 됩니다.
PUT /_cluster/settings
{
"transient": {
"knn.memory.circuit_breaker.limit": "70%"
}
}
더 보려면 왼쪽으로 스와이프하세요.
04
발문
본 논문 "대언어 모델-지식베이스 구축을 기반으로 한 지식질문응답 응용실습(1부)"에서는 지식베이스 구축 부분에 대한 사전 논의를 진행하였다. 벡터 모델 선택, 벡터 데이터베이스 튜닝과 같은 일부 주요 단계는 일부 경험을 공유하지만 상대적으로 추상적입니다. 구체적인 실제 세부 사항은 다음 부분에 주의하세요.
또한 이 문서에 언급된 코드 세부 정보는 지원 자료를 참조할 수 있습니다.
코드 저장소 aws-samples/private-llm-qa-bot
https://github.com/aws-samples/private-llm-qa-bot
워크숍 <Amazon Open Search+Large Language Model 기반 지능형 질의응답 시스템> (중국어, 영어 버전)
https://catalog.us-east-1.prod.workshops.aws/workshops/158a2497-7cbe-4ba4-8bee-2307cb01c08a/
이 기사의 저자
리 위안보
Amazon Cloud 기술 분석 및 AI/ML 솔루션 설계자는 AI/ML 시나리오의 엔드투엔드 아키텍처 설계 및 비즈니스 최적화에 중점을 두고 데이터 분석 측면에서 Amazon Clean Rooms 제품 서비스를 담당합니다. 그는 수년 동안 인터넷 업계에서 일하면서 사용자 초상화, 정제된 운영, 추천 시스템 및 빅 데이터 처리 분야에서 풍부한 실무 경험을 보유하고 있습니다.
순지안
Amazon 클라우드 기술 빅데이터 솔루션 아키텍트는 Amazon 클라우드 기술을 기반으로 한 빅데이터 솔루션의 컨설팅 및 아키텍처 설계를 담당하며 빅데이터 연구 및 홍보에 전념하고 있습니다. 그는 빅 데이터 운영 및 유지 관리 튜닝, 컨테이너 솔루션, 레이크 및 웨어하우스 통합, 빅 데이터 엔터프라이즈 애플리케이션 분야에서 광범위한 경험을 보유하고 있습니다.
당나라 Shijian
고객 빅 데이터 솔루션의 컨설팅 및 아키텍처 설계를 담당하는 Amazon 클라우드 기술 데이터 분석 솔루션 설계자입니다.
궈 렌
Amazon 클라우드 기술 AI 및 기계 학습 방향 솔루션 설계자는 Amazon 클라우드 기술을 기반으로 하는 기계 학습 솔루션 아키텍처의 컨설팅 및 설계를 담당하며 게임, 전자 상거래, 인터넷 미디어 및 기타 산업에서 기계 학습 솔루션의 구현 및 홍보에 전념합니다. . Amazon Cloud Technology에 합류하기 전에는 데이터 인텔리전스 관련 기술의 오픈 소스 및 표준화에 참여했으며 풍부한 디자인과 실무 경험을 보유하고 있습니다.
들었는데 아래 버튼 4개를 눌러주세요
버그가 발생하지 않습니다!