数学建模社区-数学中国

标题: python将红底证件照转成蓝底 [打印本页]

作者: 杨利霞    时间: 2022-9-7 11:41
标题: python将红底证件照转成蓝底
python将红底证件照转成蓝底
: h  S) W# [: I6 p1 k& E, Q前言5 v6 U* X4 `; r# s* R5 ^9 L% L
emmm…快开学了,手头只有红底证件照,但是学院要求要蓝底,这可咋办呢。懒得下ps了。自己撸起来吧。
" d3 T: O5 K/ ]7 W4 y1 F) j
/ a" |  u& {) [# h. b+ v2 {2 l
9 N) l* J6 C) }) m# r( O9 f0 n7 L$ Y5 ]  B

! U( V9 {/ M7 V6 n; w8 {% J7 _  }3 t方法一: lableme; d9 B0 @" S  ~3 W
lableme标注完后。得到一个json文件,然后将这种json文件转成掩码图.
1 l- i/ r: E% Z# [
0 Z' L. u# q( \7 {$ ?# 代码来自 https://blog.csdn.net/hello_dear_you/article/details/1201301559 w$ D; t; r2 T: b4 l
import json
. d- h+ Z2 s' ~" G+ y( l1 T  Fimport numpy as np3 D2 f7 v" _1 ?/ @" l2 C
import cv2
6 e& a; S! `# h8 X# n- {# read json file
3 D; J( B: z% K: G  b9 i' a4 jwith open("origin_json/mypic.json", "r") as f:
' w+ p4 V+ t  J4 p    data = f.read()
# Y: O+ z4 G7 H) d) R, b  `4 z5 T; A, V4 f/ M5 i
# convert str to json objs
# C0 w$ y. z: S' w6 U* h7 sdata = json.loads(data)$ s& B( X- D1 F. n$ }0 Q" A
7 {4 q$ {5 k( `" ?* S& s" n
# get the points
9 g1 B( d3 K& T& P' ]points = data["shapes"][0]["points"]
* h( A9 }% ^2 i# n7 Opoints = np.array(points, dtype=np.int32)   # tips: points location must be int32( {! q1 D. ^( t- i  H
5 p% y$ y5 Y* s( Z
# read image to get shape* g7 }0 @9 }8 G: }! s$ `& x, o
image = cv2.imread("origin_png/person.jpg")
0 O; t( m2 ^- w  x) I
1 x) Y" U8 p: O  _6 s5 ~# create a blank image3 M( L, @1 d- I
mask = np.zeros_like(image, dtype=np.uint8)) ?2 X# [+ m7 B- h
9 `7 x+ ]9 }  x" N: h/ {
# fill the contour with 2559 Y1 Y  V' @, @. u; o
cv2.fillPoly(mask, [points], (255, 255, 255))& |3 L5 L7 \: J1 l" i
1 S( F1 ~0 H) F2 \
# save the mask
: {, J+ b, D/ n, Y) q) t' Y1 mcv2.imwrite("mask/person_mask.png", mask)
2 U) S5 U+ x- a4 L- A- p1( f' [5 \6 i, l- P# p& k7 h8 g
2
& w- w# i8 K* h& T$ c3* ?' o' f! Z. B6 D) q" e
4
7 z+ I: t) v" N' k8 x$ `& ?2 B$ H5
- o% Y. F( e2 ?, E) i$ ]6 k0 d6
  r" o1 l) }. `0 i& K7
8 q& Q: M* }* b: g, g. p; p& {1 h! i1 a8
% _9 y# x) {' }" Q+ m9# G! n3 _+ a( `2 W4 J( z
108 a. W6 O" M7 [. A! V
11
) c6 ]$ y+ D0 W" I) {& P5 T1 A# C126 N9 J# c5 X2 C
13& Q! J0 P  s# `7 [" E
14
$ @3 e0 Y! |% I, L0 t7 w2 H- v15
6 A9 [' X5 z2 H4 |: U( t16
8 ?: C' T$ Y' `4 t8 z1 k17
& ^4 o/ }" }1 f/ |; e1 a4 E18
$ q6 n; ?6 X. Z; w9 H# u5 G8 u) P+ q19
! V  G5 f% A3 g$ Y4 f203 a; r5 K; ^, I* m5 i
21
0 g8 a- O, C, B: S: K$ }226 u! c2 d6 d# l4 p
23
$ n5 p# O  M2 F9 K( ]+ ~3 Q/ g2 s6 u243 {- t+ J$ i$ H5 H; I. ]
25# i* k% M' U8 @- M% T
26/ Z, i7 E; x! [% v0 l
大概是这样:
6 g2 ]$ P8 p+ ]! }: s  b
3 y) G2 K6 T5 X* Y: w* c
: k  }2 H; f" r4 e6 l' K- T2 _. i% e然后利用这个mask生成图片
) w0 ?! m2 o+ u+ l: V  A! E6 C3 }$ w+ ~, d) S" l
# 参考自: https://www.jianshu.com/p/1961aa0c02ee5 N2 Q; U, x9 d: P2 j
import cv23 l3 c; h" m  {7 |
import numpy as np
$ I# S3 `7 h8 S( R2 z1 O! U) ]: [5 P) I- H& S* Q8 H# A
8 {( {' @5 ]- b9 k0 d: l+ y
origin_png = 'origin_png/person.jpg'
1 A% f) z3 r) w! s# maskPath = 'mask/person_mask.png'3 a  t% _0 k. N
maskPath = 'mask/bmv2.png'
+ s) L. N' j4 L/ ^result_png = 'result_png/result_png.png'
% s7 i- {5 ]* f# m$ {; {
/ o' Z( B9 {4 z
0 X- S) R$ C' I( y$ f  a$ b% bmaskImg = cv2.imread(maskPath)
2 W1 b' l$ a  i0 I& {- Bimg = cv2.imread(origin_png)" h! _$ I. n3 f( f; Z% i* s  f3 \! Z
assert maskImg.shape == img.shape, 'maskImg.shape != origin_png.shape'% Q3 t3 U0 ?" e" X# @3 Z& f

6 B; m) e2 G( B/ ^h, w = img.shape[0], img.shape[1]
' Z* F6 d0 l& tprint('图片宽度: {}, 高度: {}'.format(h, w))
% U3 }3 l$ L8 n9 L, e
% R0 g; j* `, k6 X+ ]rgb = (19,122,171)7 L; l- L- L* f2 X# e0 J5 F$ R
bgr = (rgb[2], rgb[1], rgb[0])0 h2 G0 c/ g$ n
# (B, G, R)/ |: i; w! S/ R0 i7 S4 L$ @* j
for i in range(h):
: Y% s- g; [  D  p# G    for j in range(w):
! m9 \7 k+ O5 Z        if (maskImg[i, j] == 0).all():) P8 B& Z: s+ Q& T' `/ |" T
            img[i, j] = bgr3 V/ U) a1 [# m
cv2.imwrite(result_png, img)
  w' h+ Z' k9 p- L# P, Rprint('图片写入 {} 成功'.format(result_png))
' [% D; I# m! j4 t$ ^* |1" \- c) a# i) {: l3 g
26 i, L7 ?, [. [+ \/ r
3! r: ?8 W3 p: C& A6 |
45 i# u. E! e5 j! c* M0 a" b
59 B; R; L" i2 e" O7 P
6! y' U  [: H* a: k; |
7) b- X- }" S: F1 u0 W9 X' [! F5 ]
89 X2 c3 s$ p0 G
91 s+ ]" Y) w  _+ ^
10
( j3 T. M0 Y- o0 s7 N6 [* K& X+ a11
2 K  K2 w/ ^2 r8 s  i8 i127 n" P2 F" A) W$ H. Z( O! J
13
  f; \! W, r, d1 A1 G143 v$ |( f! x/ ?7 i
150 f% R- R; i( P- B, ?4 ~" l
162 S( {  u& b" I7 ~8 g2 ]
17$ V  K1 U5 Y. N( A) f
184 M: z+ L( A7 x* L* B
194 S$ l1 W, U( m# [1 k8 }# [
20
8 U5 L# q" r' v- l21
, s0 {) I/ K1 U. ]  x3 Y228 g/ u# N7 g# E0 o  r* N1 [
23: |2 A0 ~- S5 s/ d3 B
242 w* o7 c1 K3 O. q6 Q1 Z# ?  e
25
. q% G- l' S% m2 F/ O26
" ~9 A2 V" K% A+ R: u  J1 e27
% \% J8 B2 W3 q# Y' p% @& x9 r由于人长得一般,就不放图了…
+ Q5 X. C* I+ y% y% [6 F) X. A4 g- Z  J, A$ m$ Y! I$ [
缺点:
' z! C1 q7 O0 k4 Z4 |, Ilableme标注时挺费力,并且难以避免人与背景边缘会有残留红色像素的情况。% f/ w* M) x  O" t% X# ~5 g2 J( u* \
$ e1 K: e- }9 U- b3 ^. }* k

& e$ @% H' @6 {/ ?/ b# B6 f* z% a/ H- m  ~
& R1 W' @5 p1 ~% \$ P

+ x, W( q8 K1 e4 d  w. S4 g& r5 |方法二: 阈值
4 Y+ d/ W8 k' r$ f1 ~/ e" |7 w该方法通过比较像素的RGB与背景的RGB来区分是否为图像背景。
  p5 `) \& }  C; M, X% }8 X5 Q1 e! A8 E0 `* w2 J
Opencv
/ r/ n/ T# @2 ~  J5 S  Zimport cv2
9 K9 f. c: g3 {8 v0 \7 ^- u- l7 U% kimport numpy as np- }; x  Q4 }% I% A4 m3 @
$ f3 F- A* g% R5 d5 r% X
- n. f% @/ H1 t: ^4 s: K( q
def mean_square_loss(a_np, b_np):- y& a; y$ ?, w" f' T7 l2 S9 R
    sl = np.square(a_np - b_np)
0 R0 \3 L4 \: l( {  F' D    return np.mean(sl)
  _. o- X. |( ?2 T: H/ v# X6 M9 y6 V/ p/ u1 z) j
- ]; Z5 V9 a; b2 v2 ~& k5 h' ]7 x
def change_red2blue(origin_png, result_png):
+ g' M# D5 X# J" N3 W2 t    img = cv2.imread(origin_png); |2 U) O) B1 y  ]  J; r* w

6 L9 {; X  \* N: }! G4 Q    h, w = img.shape[0], img.shape[1]; H7 j7 m, Q/ c6 X' m& D9 h
    print('图片宽度: {}, 高度: {}'.format(h, w))
6 F' ]& I+ V- ~% M+ z: _) V" E9 P( e2 g; d- l( g- |
    origin_rgb = (168,36,32)  # 可以用浏览器啥的控制台工具提取出背景的rgb值" @- c* W1 M- E0 }/ U+ q
    origin_bgr = (origin_rgb[2], origin_rgb[1], origin_rgb[0])
2 p9 I: b" C: ?# G* f" Q, A+ v+ `. r    target_rgb = (19,122,171) # 蓝底RBG
; }6 {& x' W  [( k: i) _- C) |3 O- S    target_bgr = (target_rgb[2], target_rgb[1], target_rgb[0])
) F* q. f1 h( v  c) ~% {, `9 R4 J( {8 m  u$ r* N
    for i in range(h):
. Q2 Y. ?  A; L- q" Z7 b/ d        for j in range(w):
! _$ Y8 B. d7 |& v            # (B, G, R)- J& w$ j+ I' a  {
            if mean_square_loss(img[i, j], origin_bgr) < 50:
9 Q0 w/ X* X6 I" ?' i6 Z                img[i, j] = target_bgr
" ~& P& d* r$ x" \8 ]3 Z+ b6 k% }) G; n1 h0 Q
    cv2.imwrite(result_png, img)# E& _1 F" w- }7 p* @- s' m
    print('图片写入 {} 成功'.format(result_png))' l' I. B% F: x  B1 N! K, T, T* ]
( {" |2 i; y- U* C
. d! E3 m! h$ y8 B6 q- q( Q
if __name__ == '__main__':
9 i+ o$ t* z0 ]8 M: p! n    # origin_png = 'result_png/result_png.png'
# m3 c8 k% y' ~: G' K    origin_png = 'origin_png/person.jpg', L- k3 Y9 B, F- b* F
    result_png = 'result_png/result_refine.png'! A  _8 Z3 l- C
    change_red2blue(origin_png, result_png)
' R+ S5 d! i7 o5 D$ p, s1* j: a2 v# ?; s- ]4 \/ |6 o
29 v: Q$ e8 S9 E5 o7 y4 C/ N. N
3
0 ~- y* v' b8 x" W) o$ P4% a( f( b  |: g/ o& ]; L6 l! N
5
  }1 N) q4 z% n7 j0 q7 N64 ]4 S7 `0 C% l
7( ~: S( c: t7 L  o: l* q
8; Z+ g: u4 Q6 C* P# _* |% x2 o7 b, _3 o
9) f( w8 m( [& q: w7 S( L. S
10
- K( O& K' n( Q111 f7 k( v3 E  s
12
, Y% w' d8 w" J0 r* l  {13/ I7 P' u) t) J+ r  X1 B
14
/ s. }7 X, V  `5 T15
4 E- Y" g8 d7 {# ]% P  q16$ m$ U+ Q: X/ [' i+ i$ ?2 r
17) H. o! w! Z# A) x* v; L1 U
184 w2 ?2 C8 U: q9 u% R
19
- ^' J/ C4 T& H9 q+ J! j7 b201 p- [, Q$ A. U& w$ E. u, Z
21
- o" y' z2 D8 Q. _7 J- X22) T* u% E- O( k4 \+ V
23
. f6 E- h! s2 `: N" K3 P24
' K  o  {3 K( y1 n5 Z! {) ]25$ ^2 o% K' s! v( o. J
26
. ~7 `2 [! q1 u/ _27- N- A0 `% ^0 ^% }
28
; V# v. b( j; e9 ~! \* A, g299 l6 X, s' E% S9 `, P0 a
307 N- f2 |9 I6 s2 p: M5 |
315 G  U" e+ I, @$ H2 H: D) u
32' x5 c( P) r# |' d' H) `5 E
33
6 P5 a  ?: r7 `, r: Y34# _" f3 r! n7 j4 d$ K; |
35" ~4 I) a: m6 R1 P4 X. L
结果人与背景边缘仍会存在红色像素残留
8 ~& K0 \' ]$ Y1 M* t: Z7 {$ }/ d
1 |* B+ p- \6 |, s! `& V1 ]
3 Y; e1 E- b8 n' u3 I3 x* R9 ]' {6 A  e! W1 z

# B2 t( W8 ^- s4 q2 t; j
5 j) a- x# ~' U& o) MPIL+ X6 H5 q. R% C. X# J! B8 g
from torchvision.transforms.functional import to_tensor, to_pil_image
- y% g# O: t5 lfrom PIL import Image& f" O8 V/ O( _: o7 Y. I9 u$ |
import torch
0 _- N4 I; X; M% Y! C0 ^  [import time# T- L$ l7 F3 R; s+ d6 J

( a3 {- m7 u1 s# |' _
2 ^1 i. u  y1 ?7 t5 d3 x8 |  H, Idef mean_square_loss(a_ts, b_ts):6 U9 i8 u, N( G6 u$ L% K
    # print(a_ts.shape)
- N% e& f* e6 z( r# [: f5 x    # print(b_ts): w) Z0 N0 H8 ]+ j& J
    sl = (a_ts - b_ts) ** 2
# B4 v3 A/ X! o, V    return sl.sum(): l* T. _( j3 W: q- i# V+ q
9 {( I/ q* J# y4 r! y

" H7 L: B4 Y3 d3 o7 g0 F" x1 Adef change_red2blue(origin_png, result_png):" G. k. m7 ?' m
    src = Image.open(origin_png)
: b6 c% ^$ U3 Z+ k    src = to_tensor(src)( z9 |( H0 V) b: u) c' V$ G
    # print(src.shape)  # torch.Size([3, 800, 600])
3 P) z, C1 l" l; d: I& u3 k, \9 i    # channel: (R, G, B) / 255: D6 }) b% E. E# e" E1 h: x
    h, w = src.shape[1], src.shape[2]' |  ?/ P! }& R( ~

$ W, [/ u% r; G( n    pha = torch.ones(h, w, 3)
5 F$ |* G+ F& I/ |; F
* g+ i5 X! S7 B/ r+ _& ]0 K* J    bg = torch.tensor([168,36,32]) / 255
2 q4 ?1 a6 a$ Q    target_bg = torch.tensor([19,122,171]) / 255. z' `, B) Y* q; _& f9 B' k' U. @

0 @+ a4 L6 G: @- O" G& H2 i' _+ M    # C, H, W -> H, W, C( H, b* b1 q; I' S9 I+ Q& @
    src = src.permute(1, 2, 0)
5 H% @5 A$ U3 k1 ?, n+ H    for i in range(h):
+ u  g1 D# A1 v- I9 c        for j in range(w):
9 Q% h' t. t/ ~5 X: D4 i9 x4 L7 C            if mean_square_loss(src[j], bg) < 0.025: # 0.025是阈值,超参数
0 r" O! i0 w% g# e/ ]* u/ z2 j                pha[j] = torch.tensor([0.0, 0.0, 0.0])
0 l' h# {& b1 }+ I
2 |$ j1 f# B) l- b  O9 g    # H, W, C -> C, H, W1 `* T. h: u$ V# T6 w3 q
    src = src.permute(2, 0, 1)
6 Z( T7 O5 o# ?. Z- R- o    pha = pha.permute(2, 0, 1)1 X8 Q. _3 {- ?; B* K. p
    com = pha * src + (1 - pha) * target_bg.view(3, 1, 1)
$ k2 R2 D) X( n6 t, b    to_pil_image(com).save(result_png)4 n( l, D' n6 L+ v7 A9 l( e

/ h4 o2 U' X' {  Z9 q
% q) f# j2 t0 D. ]) a. E( Z  qif __name__ == '__main__':
3 g! Z: C! q) y; t$ @    origin_png = 'origin_png/person.jpg'
$ @; ~9 e. o2 N' ?' J$ ~: L6 T    result_png = 'result_png/com.png'& G, Q9 m" V6 i
    start_time = time.time()6 L% K) B. o, Y! Q
    change_red2blue(origin_png, result_png)& k  a* y) w- B8 B
    spend_time = round(time.time() - start_time, 2)
+ k; V7 a- j) \0 y- ^7 U    print('生成成功,共花了 {} 秒'.format(spend_time))
" v0 q- R, g  E" h7 v2 r8 w7 V4 R14 @$ E7 Y. U7 l5 T
2% n5 A. i4 N  S
3
5 Z+ |- i: K9 e4, |7 N# R4 H$ L. N( e) @! [
57 {' I4 k' n8 H# N" V/ L6 c
6+ g+ N# P7 @& x0 e7 r
74 K9 r* @4 a" o+ g/ q
8$ l8 _) e  ~( o. Q! x
9; e4 |( s, z* X9 ~# w
10* d' P$ s/ M8 H/ b. l8 ~
11. A; l* z2 e# D( a$ d
12
- k: E9 b1 Q/ z7 c/ b9 e13- }, {% m/ h3 Y, w6 y
14
6 Z/ q: |" w) y  N/ x# s1 N6 ]9 Z1 `15
: o5 r+ d! W0 g1 J1 Z1 [3 y16
) F4 l2 f" m$ S2 ^# x3 O$ B! C177 x# a8 C  t9 }
18& {8 i+ Z; N3 a0 [6 E2 k
19
- p4 T" u! n. u: T, L1 P20
. D- W0 b6 c/ e7 x* m+ @) i0 Y214 u1 R# j$ z4 u; t' |3 I
22
* g% r, c. D. z% g4 P2 B* Z/ B23" u! k2 o7 V8 }( X+ D
24
* W; {5 F7 ^5 x/ [! V. P( ]25" q5 x: F7 ]: ~+ A5 Q8 ?
26. J. F" G$ g6 e4 S) G
274 t* g7 u% z. q1 ]( f# R
28
- M% X8 \, ~+ P29
3 _! ]" Q: A( |( {% v8 S305 o% C; f! K1 M8 H( \. ]7 G
31
- J+ q, I% f  `32
1 ^8 f  ~. S0 D33
  L3 j; v1 ^' k341 G+ ]& {( |$ B7 ]# I: s5 ?" d
35
( t' e0 ]) r( }  G# v/ R36; F/ U( ~9 |/ |9 w: S8 b
37% g- l: Y  G9 }; @1 p2 z
38
# o& j. U; b# X' B. h3 b39
- J# ]# K2 E+ p& |40
( `4 k% B, u& x& X2 f" s41( v; E6 X& I" g, j0 C- T; J" p
421 |. r5 z' d( n9 y3 m, h
43
3 E9 c; v3 z2 d44& T, Z- ~* O9 q+ q" A
45
; D4 h$ e: n! T; t* a* m46
0 \: {1 Z* t/ O* Y. y9 s: p  {4 f该方法质量较好,但一张图片大概需要12秒。
2 s! e+ }* S& ?1 J0 |9 H- A3 l4 ^8 S
3 y' h' d6 s! z- i. ~$ o, O

4 I3 q/ [& H  i  |5 |& f9 ^方法四: Background MattingV2+ Z+ }* o+ \, C
Real-Time High-Resolution Background Matting
- p4 y# T7 J* D: F5 g7 Z4 u, |# F: M6 k4 `CVPR 2021 oral8 q$ b5 V, M* O9 z6 v

3 H) m" ?- \3 j9 R2 k论文:https://arxiv.org/abs/2012.07810
6 z" h& {# W1 W1 e0 y代码:https://github.com/PeterL1n/BackgroundMattingV27 [! @# o' _1 k1 w, b7 R

$ ?  a' w; i- L( ?- G* t6 T( lgithub的readme.md有inference的colab链接,可以用那个跑
" ^% |9 x# ~) O" v: B) K! p3 ]9 J3 e) k3 F. |
由于这篇论文是需要输入一张图片(例如有人存在的草地上)和背景图片的(如果草地啥的), 然后模型会把人抠出来。
7 B1 D' E( i+ @! ~5 M# Y$ Z& s& ?) E$ i, u
于是这里我需要生成一个背景图片。  K1 k1 T! U! i# @
首先我先借助firefox的颜色拾取器(或者微信截图,或者一些在线工具,例如菜鸟工具),得到十六进制,再用在线转换工具转成rgb。3 {/ {  ]9 M( Z
- d, _' {# c+ j- V  l; y, x
然后生成一个背景图片。4 W! P6 L- k, b( O7 M3 o

& |, X7 [7 G7 S! T7 T7 K- d0 A( dimport cv2, F" j8 G8 V  G9 ^
import numpy as np) z% L1 [' N' X; }9 C
* Q% S" E, {* o% P, ~

2 t% C! B2 I2 K& w1 w' iimage = cv2.imread("origin_png/person.jpg")4 w- n+ M  r: K# i; m
origin_rgb = (168,36,32)  # 可以用浏览器啥的控制台工具提取出背景的rgb值
# J6 h8 u% F9 q1 T  `3 Q8 g; {+ n9 Zorigin_bgr = (origin_rgb[2], origin_rgb[1], origin_rgb[0])
9 i& T+ F% l9 n4 h( ?* I- m) Iimage[:, :] = origin_bgr
% q" {! ^" X6 w) P& R; g9 ?7 @3 y2 _' _, i4 h$ \$ m* z4 r
cv2.imwrite("mask/bg.png", image)
) C( A; ]* ~5 ]6 l3 U1
* o: Z( w2 L9 E/ d. S0 N" u( e/ h2
/ d5 v: @4 M( M5 X3/ a6 {# A, K9 b! k2 h% Q
40 V  J: o% Z" @8 c
5
4 X$ I3 R8 Y0 d: D9 e: O6
0 K3 H3 i' Q7 S0 @: E$ I  [7
8 s0 o/ h& J* R( p! t8" d, W# q: ~( G. S* E
9
+ J4 |' k/ `+ F: O" h3 |10: M5 F8 q6 E; S+ \( o- ]7 `0 I. _

/ b" v7 h6 h+ G$ |! ~. N% \- W需要上传人的照片和背景照片, 如果名字和路径不一样则需要修改一下代码/ y/ Q% L' y8 ^7 G. C) `( i; j! z
: N/ |0 K1 ?/ v
src = Image.open('src.png'); g- }' c7 g9 F2 w1 ~/ ?
bgr = Image.open('bgr.png')
  i( s  ^2 x' c1
- `4 O) w' l# Z, K9 ]+ P2
3 l0 u7 z1 F; B+ i9 a* p另外原论文是边绿底,要变蓝底,白底,红底则可以修改RGB值,举个例子,原来是这样的(绿底, RGB120, 255, 155)
) J) k. c) E5 ]5 E
0 @1 Z! f) k) ~; n1 D! Y* hcom = pha * fgr + (1 - pha) * torch.tensor([120/255, 255/255, 155/255], device='cuda').view(1, 3, 1, 1)
( Y  n6 Y) K1 W' ]# J& n1
* F) A) Z2 i" S2 u, ^2 T. c5 _7 E: G2 b# S: _' c
那么加入我要换白底(255, 255, 255),就是% U" }1 m' E4 A5 Z* J4 c
( W9 F5 T3 x' O& \% g3 \
com = pha * fgr + (1 - pha) * torch.tensor([255/255, 255/255, 255/255], device='cuda').view(1, 3, 1, 1)- G; j  p* @/ q, e
1" |+ w2 z+ X; L$ A7 q1 x4 m% o. K

0 r' `1 @! ^) s) `, _. Z, Z: i假如像我换蓝底(19,122,171)具体深浅可以调节一下RGB,就是9 C' R( P1 a: ?) m3 ]" p

# F4 _7 k$ y0 ]) ~! w4 C5 ucom = pha * fgr + (1 - pha) * torch.tensor([19/255, 122/255, 171/255], device='cuda').view(1, 3, 1, 1)
2 [7 r! e) b+ @16 R" @2 @5 h8 M* U( `; J
总结: 其实这种方法从 任何颜色的照片 都可以 换成任何颜色的底。只要换下RGB.
, w& j: Y! [+ j' c, R. M  P' r/ W: V4 W9 Q! g
然后就输出图片了。可以看到效果相当好。不愧是oral。
3 Y! d  C$ J6 ]8 r. c
, y4 U& W" e1 W* h& Z8 W; |
5 d5 S5 D) D; M  }原论文可以实现发丝级效果
  J. F. p; K9 h. Q' t1 y
+ P1 w$ _# `. n0 @& h3 Y5 e1 y% {5 U
0 m7 o* l- k0 t! L: j" F
: m( [7 D! B# a: X4 s* ^( v1 X# v7 _$ {9 {. @
& y  E; n/ i  n
报错解决方案1 H' h1 L3 f: m$ C
can’t divided by 4 / can’t divided by 16, [2 {- ^" T! C; u1 j4 d2 \
由于该骨干模型可能进行4倍或16倍下采样,因此如果您的证件照不是该倍数的话,有两种选择方案。一种是padding, 填充后再送入模型,然后出结果后再用clip函数裁剪。另一种方式是resize, 给resize到规定倍数的宽和高。
" Z7 H0 B4 `" b( `8 m& ]) Y5 Z这两种方案需要的代码都可以从这篇博文找到: python图像填充与裁剪/resize
- E7 f. h( c! ]4 k————————————————* R) U6 Z1 L" h, B8 u
版权声明:本文为CSDN博主「Andy Dennis」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。2 v& E: G: y8 b& f% ~/ L; _! s: z  K
原文链接:https://blog.csdn.net/weixin_43850253/article/details/126376767
. t, p  I+ o7 Y8 v& U/ m8 c% b+ i  d' V9 Y. N6 S6 h! q! F" X

# [0 m* T+ z) T/ a+ |6 [4 e




欢迎光临 数学建模社区-数学中国 (http://www.madio.net/) Powered by Discuz! X2.5