레퍼런스 이미지를 주고 캐릭터 영상을 만드는데 요청한 동작이 안 나오고 계속 서 있는 자세로 돌아온다면, 프롬프트를 고쳐 쓰기 전에 레퍼런스 네 장이 전부 서 있는 사진인지 보십시오. 저희는 프롬프트 쪽을 먼저 고쳤고, 측정해 보니 아무것도 달라지지 않았습니다.

무엇을 바꿨고 무엇이 달라졌나

학습셋을 세 벌 만들었습니다. 배경 열두 곳과 시드는 세 벌 모두 같고, 대조군은 같은 동작을 열두 번 반복합니다.

첫 번째(v2)는 손 흔들기와 박수처럼 서 있는 자세의 상체 제스처 열두 가지입니다. 두 번째(v3)는 그 어휘를 통째로 갈아엎어 높이 점프, 바닥까지 웅크리기, 제자리 회전, 가로질러 달리기처럼 몸 전체가 움직이는 동사 열두 가지로 바꿨습니다. 레퍼런스는 v2와 같은 네 장을 그대로 썼습니다.

세 번째(v4)는 반대로 했습니다. 프롬프트와 시드를 v3와 한 글자도 다르지 않게 두고 레퍼런스 네 장만 바꿨습니다.

레퍼런스 네 장의 차이 위가 v3까지 쓰던 레퍼런스입니다. 표정은 넷 다 다르지만 자세는 넷 다 서 있습니다. 아래가 v4로, 정지와 걷기와 점프와 웅크림으로 자세 공간을 덮습니다.

결과는 이렇습니다. 아래 수치는 열두 클립이 서로 얼마나 다른 움직임을 보이는지를 대조군과 비교한 것이고, 클수록 다양합니다.

학습셋 레퍼런스 프롬프트 대조군과의 차이 p
v2 서 있는 자세 네 장 상체 제스처 열두 종 +0.0173 0.010
v3 v2와 동일 전신 동작 열두 종 +0.0172 0.016
v4 자세 네 종 v3와 동일 +0.0272 0.0025

v3는 v2와 소수점 넷째 자리까지 같습니다. 프롬프트 어휘를 전부 갈아엎은 대가가 0.0001입니다. 레퍼런스만 바꾼 v4에서 분리가 58퍼센트 커졌습니다.

같은 프롬프트, 다른 레퍼런스 같은 여섯 프롬프트를 같은 시드로 생성한 것입니다. 위가 v3, 아래가 v4입니다. 웅크리라고 했을 때 실제로 바닥에 내려앉는지, 넘어지라고 했을 때 실제로 쓰러지는지를 보십시오.

레퍼런스는 외형만 정하는 것이 아닙니다

레퍼런스 조건 생성에서 레퍼런스는 보통 “이 캐릭터가 어떻게 생겼는지”를 알려주는 장치로 설명됩니다. 실제로는 자세도 같이 알려줍니다. 네 장이 전부 서 있으면 모델은 이 캐릭터가 서 있는 존재라고 배웁니다. 프롬프트로 웅크리라고 말해도 레퍼런스가 계속 서 있으라고 말하고 있으면, 둘 중 이기는 쪽은 레퍼런스입니다.

실용적으로 중요한 이유는 비용입니다. 프롬프트를 다시 쓰는 일은 공짜처럼 느껴지고 그래서 먼저 손이 갑니다. 레퍼런스를 다시 만드는 일은 이미지를 새로 생성하고 골라야 하니 번거롭습니다. 저희는 싼 쪽을 먼저 했고 그게 헛수고였습니다. 순서가 반대여야 했습니다.

시드를 늘려도 검정력이 안 샀습니다

여기서 정직하게 적을 것이 많습니다. 위 표의 세 세트는 각각 열두 클립이고, v3와 v4를 직접 맞붙이면 p가 0.148로 유의하지 않았습니다. 그래서 시드를 두 벌 더 뽑아 세트당 서른여섯 클립으로 늘렸습니다.

세 시드 모두 부호가 같았고 효과 크기도 +0.0100, +0.0082, +0.0096으로 거의 붙어 있었습니다. 합쳐서 재도 p는 0.123이었습니다. 이상한 쪽은 따로 있었습니다. 클립을 세 배로 늘렸는데 우연이 만드는 폭이 거의 그대로입니다. 0.0097에서 0.0087로 줄었을 뿐입니다.

원인은 독립 단위였습니다. 세 시드가 같은 열두 프롬프트를 씁니다. 클립은 서른여섯 개지만 서로 다른 질문은 여전히 열두 개고, 시드를 더 뽑아봐야 같은 질문에 같은 답을 반복해서 듣는 것에 가깝습니다. 검정력을 사려면 시드가 아니라 장면과 동작을 늘려야 했습니다. GPU 여섯 시간을 쓰고 배운 것입니다.

그래서 통계를 구조에 맞게 바꿨습니다. v3와 v4는 같은 프롬프트를 공유하므로 프롬프트마다 짝지을 수 있습니다. 프롬프트별로 그 클립이 같은 세트의 나머지와 얼마나 닮았는지를 구해 짝지어 검정하면 p가 0.0151, 부호검정으로 0.0269입니다. 유의합니다.

다만 이건 통계를 바꿔서 얻은 유의성입니다. 먼저 돌린 검정이 유의하지 않았고 두 번째 것이 유의했습니다. 근거가 타당해도 모양은 p-해킹과 같습니다. 제 편을 들자면 통계를 바꾼 이유는 결과가 아니라 귀무분포가 안 줄어든 것을 보고 원인을 진단한 데서 나왔습니다. 그래도 통계를 미리 정해두지 않은 것은 사실입니다.

정리하면 이렇습니다. 프롬프트 어휘를 바꾸는 것이 무의미했다는 쪽은 단단합니다. v3와 v2가 소수점 넷째 자리까지 같은 것은 검정이 필요 없습니다. 레퍼런스 자세 쪽은 방향이 세 시드에서 일관되고 짝지은 검정에서 유의하지만, 세트 단위 검정으로는 아직 아닙니다. 두 숫자를 다 보고 판단하시는 편이 낫습니다.

지표가 배경을 재고 있었습니다

이 결과들을 내기 전에 지표부터 고쳐야 했습니다. 동작 다양성을 재려고 프레임 차분에서 모션 서명을 뽑아 클립끼리 비교했는데, 처음 구현은 프레임 전체를 썼습니다. 클립마다 배경이 다르니 카페의 김과 해변의 파도와 눈길의 조명이 전부 “움직임”으로 들어왔습니다.

중앙 60퍼센트만 남기고 다시 재자 귀무분포의 표준편차가 절반 이하로 줄었고, 그 전까지 “유의하지 않음”이던 판정이 두 건 뒤집혔습니다. 배경을 다양화하라는 조언과 동작 다양성을 재라는 요구는 같이 가는데, 배경을 다양화한 순간 전체 프레임 지표는 못 쓰게 됩니다.

임계값도 손으로 정하지 않는 편이 낫습니다. 두 세트의 클립을 한 통에 붓고 무작위로 다시 가르기를 이천 번 반복하면 “우연히 이 정도 차이가 날 확률”이 그대로 나옵니다. 저희가 처음 쓰던 임계 0.05는 그렇게 만든 분포의 95퍼센트 지점보다 네 배쯤 높은 값이었습니다.

학습보다 제로샷이 안정적이었습니다

같은 실험 줄기에서 나온 별개의 결과도 하나 붙입니다. 레퍼런스 조건 어댑터를 직접 학습시킨 것과, 학습 없이 제로샷으로 조건만 준 것을 네 개 시드에서 비교했습니다.

정체성 유사도 자체는 두 방식이 구분되지 않았습니다. 갈린 것은 안정성입니다. 한 클립 안에서 프레임마다 정체성이 얼마나 흔들리는지를 보면 학습한 쪽이 유의하게 더 흔들립니다. 얼굴 인식 기반 지표에서 0.153 대 0.071이고, 얼굴이 필요 없는 임베딩 지표로 다시 재도 0.082 대 0.055로 방향이 같습니다. 서로 다른 두 계기가 같은 말을 하고 네 시드 전부에서 부호가 같으면, 그건 시드 운이 아닙니다.

부수적으로 레퍼런스를 네 장 주는 것이 한 장 주는 것보다 정체성을 잘 지킨다는 것도 두 계기 모두에서 확인됐습니다. 이쪽은 학습이 필요 없고 추론할 때 인자 하나 바꾸는 일이라 당장 쓸 수 있습니다.

다양한 학습 데이터가 사주는 것은 다양성이 아니었습니다

같은 줄기에서 하나를 더 재봤습니다. 어댑터 두 개를 똑같은 설정으로 학습시켰습니다. 스텝 수도 랭크도 레퍼런스도 같고, 학습 클립 열두 개가 열두 가지 동작을 담느냐 한 가지 동작을 열두 번 반복하느냐만 다릅니다. 그리고 두 학습셋 어디에도 없는 홀드아웃 동작 열두 개를 생성시켰습니다. 배운 동작을 다시 재생하는 건 일반화가 아니니까요.

기대는 열두 동작으로 배운 쪽이 처음 보는 동작도 더 다양하게 그리리라는 것이었습니다. 틀렸습니다. 두 어댑터의 출력 다양성 차이는 우연히 생기는 폭의 8분의 1이었고 p는 0.42입니다. 학습셋을 다양하게 만든다고 출력이 다양해지지 않습니다.

대신 다른 게 움직였습니다. 같은 프롬프트로 짝지어 보면 한 클립 안에서 캐릭터가 흔들리는 정도가 0.0384에서 0.0133으로 65퍼센트 줄었습니다. 평균 정체성은 통계적으로 같습니다. 가장 먼저 의심한 것은 “12액션 쪽이 덜 움직여서 덜 흔들린 것 아닌가”였는데, 움직임 양의 차이는 유의하지 않고 스물네 클립 전체에서 움직임과 흔들림의 상관이 사실상 0이었습니다.

홀드아웃 동작 비교 학습에 없던 동작 네 가지입니다. 클립마다 앞·중간·뒤 세 프레임을 뽑았습니다. 요청한 동작이 제대로 나오지 않는 것은 양쪽 다 마찬가지고, 볼 것은 세 프레임 사이에서 캐릭터가 얼마나 유지되는지입니다.

한 가지 동작만 본 어댑터는 처음 보는 동작을 요구받으면 프롬프트와 싸웁니다. 그 갈등이 정체성 흔들림으로 나옵니다. 다양한 동작을 본 어댑터는 싸우지 않습니다. 학습 데이터의 다양성은 출력의 폭이 아니라 낯선 요청 앞에서의 안정성을 삽니다.

ThakiCloud 관점

캐릭터 설계와 레퍼런스 생성, 학습셋 구성, 어댑터 학습, 평가까지 전부 사내 GPU 안에서 닫혔습니다. 브랜드 자산인 캐릭터 이미지가 외부 API로 나간 적이 없습니다. 학습이 필요한 국면은 Maxis가, 생성과 서빙은 Metis가 맡습니다.

이 실험에서 실제로 남는 것은 재볼 수 있었다는 점입니다. “레퍼런스 자세가 동작을 제약한다”는 가설은 그럴듯하게 들립니다. 그럴듯한 가설은 대부분 틀립니다. 자기 데이터로 재보지 않으면 프롬프트만 계속 고쳐 쓰면서 왜 안 되는지 모르게 됩니다.

이 글의 이미지와 영상은 전부 사내 GPU에서 생성한 것이고, 수치는 시뮬레이션이 아니라 실제 측정값입니다.

태그: character-consistency, 평가, reference-conditioning, video-generation, wan2

카테고리:

업데이트: