QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 3447|回复: 0
打印 上一主题 下一主题

深度学习和目标检测系列教程 8-300:目标检测常见的标注工具LabelImg和将xml文件提...

[复制链接]
字体大小: 正常 放大
杨利霞        

5273

主题

82

听众

17万

积分

  • TA的每日心情
    开心
    2021-8-11 17:59
  • 签到天数: 17 天

    [LV.4]偶尔看看III

    网络挑战赛参赛者

    网络挑战赛参赛者

    自我介绍
    本人女,毕业于内蒙古科技大学,担任文职专业,毕业专业英语。

    群组2018美赛大象算法课程

    群组2018美赛护航培训课程

    群组2019年 数学中国站长建

    群组2019年数据分析师课程

    群组2018年大象老师国赛优

    跳转到指定楼层
    1#
    发表于 2021-7-14 15:18 |只看该作者 |倒序浏览
    |招呼Ta 关注Ta

    7 f0 D0 I1 @+ e! w) @8 J深度学习和目标检测系列教程 8-300:目标检测常见的标注工具LabelImg和将xml文件提取图像信息
    / m5 C8 g" ?; p6 C图像标注主要用于创建数据集进行图片的标注。本篇博客将推荐一款非常实用的图片标注工具LabelImg,重点介绍其安装使用过程。如果想简单点,请直接下载打包版(下载地址见结尾),无需编译,直接打开即可!
    , y; \; g& {+ Z+ o' }) A5 U# O" Y6 j% }+ I6 D
    6 t) E( P6 A4 ?; N1 v3 R
    感谢原作者对Github的贡献,博主发现软件已经更新,可以关注最新版本。这个工具是一个用 Python 和 Qt 编写的完整的图形界面。最有意思的是,它的标注信息可以直接转换成XML文件,这和PASCAL VOC和ImageNet使用的XML是一样的。$ I" c6 f" K( X. b$ m0 H" D' W

    " T4 R2 e" y9 @% Q  \& x# o

    , a" a$ e  r( L- ?  c附注。作者在5月份更新了代码,现在最新版本号是1.3.0,博主亲测,源码在Windows 10和Ubuntu 16.04上正常运行。+ v9 k7 X3 m4 l+ `3 W: A" j; b
    + a( b/ X: @% T  {: R. Y* u, ?& Y

    : s, d% ]1 b$ g. Q+ `; |3 ~  {具体的安装查看Github教程:https://github.com/wkentaro/labelme/#installation( {" ]! Q% D9 G0 n
    / m% i8 A% O+ l: ?5 }  y

    5 j. c) n: m  y在原作者的github下载源码:https://github.com/tzutalin/labelImg  [7 g! t: ?. M; c( e( z+ o
    。解压名为labelImg-master的文件夹,进入当前目录的命令行窗口,输入如下语句依次打开软件。
    2 m3 c8 q# \7 t0 {
    - l( H- i/ k4 k

    0 }1 ~! Z3 `/ Apython labelImg.py0 g  j% y6 o1 Y" X$ m' R
    1
    * z4 {4 T# J( z" c* \, s6 o3 F
    8 ^9 s; Y/ _& U  |/ R
    8 e8 F2 s7 |, J# h* L6 O0 W( X/ t% H
    & [( ?; S0 p" A; {
    / `, U& M+ `. ]7 s
    具体使用
    , I: H2 U: Y8 `: c2 C修改默认的XML文件保存位置,使用快捷键“Ctrl+R”,更改为自定义位置,这里的路径一定不能包含中文,否则不会保存。5 B6 Q2 t% f: P: ?: N

    1 V3 E9 N! f' s- u* R

    - w* f1 z3 p* [) Z# p- @. L使用notepad++打开源文件夹中的data/predefined_classes.txt,修改默认分类,如person、car、motorcycle这三个分类。5 K. e$ K1 I) ]3 Z/ M, x

    5 _  P; p; u( |5 K$ x/ N% {7 X
    , C% C2 U( n0 n
    “打开目录”打开图片文件夹,选择第一张图片开始标注,用“创建矩形框”或“Ctrl+N”启动框,点击结束框,双击选择类别。完成一张图片点击“保存”保存后,XML文件已经保存到本地了。单击“下一张图片”转到下一张图片。
    ) U3 }7 I9 J7 J: ^: w
    0 T6 G) A. N! P0 s: w, Z
    8 c0 ]$ P$ L5 |! a% v8 `
    贴标过程可以随时返回修改,保存的文件会覆盖上一个。
    7 d8 V8 ?5 n7 g7 ?/ o
    ; v7 {. q7 Y1 i9 b0 L
    - @* z7 J& X7 n" D' k5 p
    完成注解后,打开XML文件,发现和PASCAL VOC格式一样。; |# ?" {$ i! a0 c% X. v, e
    8 q: ]/ T/ J9 t! m" d

    2 X6 ~& C4 J9 j; b/ U将xml文件提取图像信息
    ; ]( Y8 S$ o( N下面列举如何将xml文件提取图像信息,图片保存到image文件夹,xml保存标注内容。图片和标注的文件名字一样的。
    0 A3 M; Y  j* t
    / M, ^- A/ V! k7 }$ r
    / D0 _1 n4 Z( b0 p! @: A$ \

    ( X  a( P8 _; z2 |) s

    $ I- Q; X! A1 X) ~下面是images图片中的一个。8 E" l% S3 ~& V" D

    / N9 d' ?3 L$ Z: A0 A2 O/ h9 q$ B5 |! \7 \

    ; R8 y# w7 v: Z下面是对应的xml文件。' c. l( V: W  f

    / `! L( Z* c6 r( S+ f% }
    & m" {5 N! H0 y* G' `/ g
    <annotation>
    $ \$ D9 Q) [. ~% X/ Z4 I0 `- U        <folder>train</folder>
    % x: _1 ^. S( n2 }% @        <filename>apple_30.jpg</filename>- g! q9 ~+ S; t3 s( `' q- n
            <path>C:\tensorflow1\models\research\object_detection\images\train\apple_30.jpg</path>
    7 ]- j& S, @$ n: X3 K$ R        <source>
    5 }- }6 m/ w7 F6 j- B                <database>Unknown</database>
    ) n0 \5 s  a9 O& G! A1 c7 d- }        </source>
    % S) G& e  t, o" U$ f        <size>, v6 d, d) s7 \, F8 A, r
                    <width>800</width>
    6 c3 |' n+ C2 W1 V; a; b                <height>800</height>
    + D. |/ \- n  F) v                <depth>3</depth>8 ^; ?7 s5 v( T0 }; i7 {% b
            </size>: K! }. J# K/ \& b+ t
            <segmented>0</segmented>
    3 u- c  a7 H  o3 D        <object>
    2 Y! H2 q9 S/ |+ B% Q/ i3 f+ o                <name>apple</name>
    ' ]( u# O6 B) W2 J                <pose>Unspecified</pose>% I& e* I9 H% u
                    <truncated>0</truncated>5 B6 b0 @  V1 E; U5 d
                    <difficult>0</difficult>
    % t9 b, T/ ]  W. J- ~                <bndbox>1 i7 l1 b' Q* o7 O  {" J8 B
                            <xmin>254</xmin>
    ( G4 O+ Z  c% a* ]! r                        <ymin>163</ymin>9 G( S3 r' M0 D0 t+ J# f
                            <xmax>582</xmax>" D& G. C# E( }' X1 z" l, Z
                            <ymax>487</ymax>* k+ e" y2 o$ d  c
                    </bndbox>% ~5 i2 Q5 u9 C- M: T5 l
            </object>) u1 v0 ]5 v5 s8 y* K
            <object>
    " S! |# s$ H7 @3 f5 ]                <name>apple</name>. F8 F8 v5 K) r. m& J' ]
                    <pose>Unspecified</pose>
    ' E. [1 W3 f! [  C, @) F0 A. c                <truncated>0</truncated>
    * \! @. K7 t$ l' r2 l& X3 g4 |0 N! g                <difficult>0</difficult>
    6 P- d( Y( i5 {5 y) l1 D# W                <bndbox>
      |; T3 E6 z) {% r+ F                        <xmin>217</xmin>9 A% _. S+ y" S
                            <ymin>448</ymin>6 z( h0 K% F# c! Y
                            <xmax>535</xmax>
    , D4 g7 l5 M* G* ~7 w                        <ymax>713</ymax>
    ' \/ I$ b2 ]/ }5 ?& K9 y0 m+ \; v# h2 r                </bndbox>
    ; m' A6 H; w$ Q& k, ~7 I; e        </object>' t/ s7 u' k( r# t1 }6 N
            <object>
    2 Q- g9 Z6 h. {# ^3 p' u                <name>apple</name>
    ; m' [" M* L8 H+ z1 ?                <pose>Unspecified</pose>
    ; o9 s. T  z+ n; x) D8 ~+ u7 U                <truncated>1</truncated>
    ( b/ H- p2 ^+ E5 n. n& Y                <difficult>0</difficult>
    ! \! O. f/ Z4 o9 e8 V                <bndbox>
    6 d! Y4 ]: R; {                        <xmin>603</xmin>
    5 `/ c; O# E  F1 g: E                        <ymin>470</ymin>8 \2 K' ]# V+ t& l
                            <xmax>800</xmax>
    0 K* i" l. V) a; {( Y& z( `0 Z* P                        <ymax>716</ymax>
      M5 R7 z% L4 W                </bndbox>7 O$ X( Z/ A5 a& g: {  o8 I& @: u
            </object>
    # k8 A# x, E: M1 j        <object>
    9 Q, F$ B) j" D5 E3 k0 m& {/ S# r                <name>apple</name>
    4 S# E" R/ }5 J$ Z6 o                <pose>Unspecified</pose># b' b# R- G1 L2 x9 p
                    <truncated>0</truncated>
    8 S' ?& l4 O# X7 C, ~6 R6 q1 e                <difficult>0</difficult>
    6 O, A* C( r8 @% z; a                <bndbox>8 j7 e1 |& t: @3 Z
                            <xmin>468</xmin>
    : ^3 t: Z( B) ]3 H* ]6 w3 D5 }; h4 l                        <ymin>179</ymin>$ T8 H/ y/ \+ _0 w4 L
                            <xmax>727</xmax>6 R5 L# r" n& @9 s$ v( k3 x
                            <ymax>467</ymax>
    9 O" q" X/ f& E% r! G                </bndbox>
    & J: V! y, B6 K  b) m        </object>6 [3 E) o9 `1 I$ Q5 T# E, N
            <object>* S$ m6 w" O. U+ z0 j
                    <name>apple</name>. F) I" a4 a4 c
                    <pose>Unspecified</pose>
    . @! E9 H, m: n                <truncated>1</truncated>
    - r8 k5 a$ q# f6 ^                <difficult>0</difficult>3 H  l7 m& u  n
                    <bndbox>
    6 [( o; n, K* o' ~9 p- W# j5 d                        <xmin>1</xmin>+ T$ }1 E2 w5 B, e" u! k2 f
                            <ymin>63</ymin>
    $ a, N! b1 u) f+ b                        <xmax>308</xmax>  q) q2 `% O. _$ I0 ^% g* h7 \
                            <ymax>414</ymax>
    - D: X, C+ p& G# g' P; j3 M( V/ \                </bndbox>8 }9 d& o3 T  M
            </object>" m, f( \$ |# [) {
    </annotation>
    8 h* ~2 Q+ M  u5 L' h3 f1" a% `0 T1 k0 Y# E: r7 [" ~. _
    2
    ' n; C8 u; c/ o3
    ! Y+ }' }; t( ~" M, `! C  g4
    5 {( G5 M5 t: z7 B! l1 B; {5
    ' n3 X" @. G1 a5 t6
    . q- X2 a& x+ p: [& J8 S9 u7
    ' X1 L2 _8 U0 Q' f$ X' R8
    ! u3 |6 v: b" m/ f9
    3 `6 G. f. D- s. K, P  @10, c4 K/ i% W' n' B1 J/ E
    110 B+ k& w( ]6 G% ?9 S0 ]
    12) j; B/ z  J# \
    138 O  g. T( o# N
    14
    " n5 n1 _' S1 e: l/ |+ U: A15
    & s3 C& r( d/ Z/ l5 m% A4 @  Z16
    / v9 z8 P0 _5 F) l$ I17
    ' o8 Q9 E/ \3 i18
    ! c, }9 V0 @8 w! e" N8 b: |195 O7 b7 `. w3 g: n
    20
    9 _- J8 v# d9 s( X21+ K( F' a* \9 c, g; j$ k* U
    22
    ; Y: s5 a/ f% I8 r23
    4 V( e; h. |3 M24& e1 G  k8 b: a4 T
    256 Z3 e8 a% }# ~  t* m9 l
    269 r. O; r* Y: n: h
    27
    7 N$ e, P/ j5 M; M' S7 k28
    4 H5 C  c" }3 O8 ~( S1 c7 k29
    8 r2 ~; z9 g! Z; X- T. U30
    ; L9 s* m6 M* Y  P31
    0 c& w; z" k, S9 Z8 _; O0 d  V32( q" ^: n* i' t) G$ z! M% L
    33& A# v* w( Z0 u# `
    34  z" g/ S. P+ T& e6 D6 d
    35
    8 t) X" b# }$ x1 M# ^; ~/ w- l8 l36: T% Y& }# r6 ]! W
    37
    5 \" \+ k* {$ k0 b38
    , P( o. d) {9 g39
    , b) ^3 N8 |% |6 [' s. c40
    9 \9 r) U: S* B  ~  P41
    - M" K/ w9 H; O- V; H  w42
    - A$ q3 L  {2 r/ s7 |" m43
    + ~, U9 L/ T. ]# [: @+ Z3 R: L44' k2 h/ @6 Y* `( u
    45: Z$ _4 n7 z/ Y3 |
    46
    4 W3 r3 U- n* \8 X, {, g' X47
    . ?% ^) T4 Y  g' _& M) u48( x9 n9 s( P. I& U/ B5 h2 v
    49
    ! K9 k+ c+ s2 j% }  s, X* K; m( }% u50% ~% V0 @6 t( @+ x$ I( p1 ]
    51& Y" B: y* E( X# M+ f
    52+ p, r0 t$ h5 j3 N
    53
    $ L3 \0 ?5 p% P* N542 F7 Q+ Y9 e9 B
    55
    $ r# c6 v+ L1 v2 ]  P561 D  ^) d# n" A# ?
    57
    , G6 g" a, m6 X7 T& D588 f' I" c, q- k" k' \# N7 u+ Q/ }+ ]- x
    59
    0 }8 Y0 ]1 K0 L- |! U  \2 w7 a5 }60
    9 D9 s/ K7 z1 O  k617 i* |0 {4 u- X' S. [& k
    625 i2 u5 y4 P4 d# D  N' U
    63
    & O5 ?; i) I" ?64  {4 n' h. Z1 x- x" G+ z! |
    65
    - \- O+ }$ e* [0 R& |66
    7 [1 N" z0 D0 {9 l67
    : G( J6 A  t' T. n68
    $ r0 D! L9 T5 {( J" J, K69
    / {! z9 _/ X* g8 Y709 T: v- j. z3 p" _/ a# J5 h4 r8 L
    71- s1 \) B# D$ d
    72
    3 k" g1 {; \1 L0 f5 L9 F73* u/ y/ @6 r/ S9 o% k1 D
    743 O6 a* K" u2 L* x( x; |
    将xml文件提取图像信息,主要使用xml和opencv,基于torch提取,代码比较凌乱。
    $ r& b  ^6 E* {7 D1 H4 Z& K' r
    " P5 m& H7 Y; K) a, k

    0 Z0 T5 m; N# p- _; S4 D3 M2 t; Rimport os5 G! i" j! u1 u% R. R( f
    import numpy as np0 z9 j9 I7 h! e6 I
    import cv29 G# F  I" @, j3 }; @: }* S
    import torch( e' E( c- D7 {% x* D) U5 T
    import matplotlib.patches as patches
    ' Y7 k' D7 I) K. T2 Q+ Dimport albumentations as A
    & F- e; U1 G$ u, @; b' W& Gfrom albumentations.pytorch.transforms import ToTensorV2* i2 S  O' w" L0 {) z
    from matplotlib import pyplot as plt
    1 F) ?; \6 a% G( G! J' j  H, a* d  N* Cfrom torch.utils.data import Dataset
    ! N% i( ^) L+ F: efrom xml.etree import ElementTree as et6 B$ I$ |. o( v) c4 x; p9 }
    from torchvision import transforms as torchtrans
    # m2 o* K% i% W$ U4 g
    7 E" N# ]8 m, J8 u2 i: p
    + w" u6 H; p" u, S4 d: x" j
    # defining the files directory and testing directory
    / b6 N. d. x; S/ Ftrain_image_dir = 'train/train/image'
    5 a" R, G8 K+ f% M3 ntrain_xml_dir = 'train/train/xml'
      F4 x* B4 V( U1 h- H$ V) L5 M# test_image_dir = 'test/test/image'6 t, \0 L' G+ e5 L; m. b
    # test_xml_dir = 'test/test/xml'
      U  m& o. m$ a0 J
    5 H+ V8 t# v6 o& ~$ V) F
    % w" \$ G/ O# J1 o: E( y
    class FruitImagesDataset(Dataset):! [2 X# P  [& f5 C) V
    4 P2 V9 h0 S% T. h6 q  e  v

    ! Q! T) F+ i! {% p) [2 d- p    def __init__(self, image_dir, xml_dir, width, height, transforms=None):3 x# i2 e/ o, X
            self.transforms = transforms/ r4 R. }7 ~4 x" n, u! |; ^9 ]
            self.image_dir = image_dir
    2 V* a$ ^: a, h9 ^6 S* `1 g        self.xml_dir = xml_dir7 r; l+ n$ L: Y  I# L1 T
            self.height = height- {/ M% P4 p& y6 M# ?$ l
            self.width = width2 `1 P0 J5 ^* E$ P5 h3 n
    3 B9 f4 v$ d3 x
    & N. H1 I/ s7 F! r
            # sorting the images for consistency
    ! g* I# a1 M. y8 Y) D( a        # To get images, the extension of the filename is checked to be jpg
    8 _1 M( S) Q. i+ q        self.imgs = [image for image in os.listdir(self.image_dir)7 W9 r  v' K+ {1 R$ I+ a7 n
                         if image[-4:] == '.jpg']5 R$ G, f4 @: ]
            self.xmls = [xml for xml in os.listdir(self.xml_dir)
    / u8 t; M! g) t. }) `4 ^+ S, I                     if xml[-4:] == '.xml']
    9 E9 a: a8 ~- j8 L& x! R+ G. D$ s/ K5 J" u, k

    0 b5 N7 }- ^' |* o        # classes: 0 index is reserved for background
    / k/ w& G0 ?/ K+ b0 d        self.classes = ['apple', 'banana', 'orange']' X  u  z1 b: B. ^/ n

    5 b) R7 _6 @$ I- i$ K0 h, @! H
    $ O3 Z# E8 _8 b3 [( w  N
        def __getitem__(self, idx):" k: j. [$ B9 L

    ; C, u4 Y1 E& h: M$ _2 L) o

    $ b( t: r! b1 C  u3 T2 h        img_name = self.imgs[idx]
    2 I9 M! W/ b. `( J" X$ W* x        image_path = os.path.join(self.image_dir, img_name)
    $ a$ w. m6 p- ?3 p4 l4 H8 \2 T7 q
    4 G) h9 V0 ~' q7 e9 M, v
            # reading the images and converting them to correct size and color
    & P. @3 ]- ^, ^1 r$ S        img = cv2.imread(image_path)
    ( \* p/ j* K$ H+ a4 k* Y        img_rgb = cv2.cvtColor(img, cv2.COLOR_BGR2RGB).astype(np.float32)4 I) u, Q. C4 v" g  o
            img_res = cv2.resize(img_rgb, (self.width, self.height), cv2.INTER_AREA)
    4 m& t# ]) K" I% @, o8 X' N# W        # diving by 2551 q# {! i4 L* K1 h+ s9 T
            img_res /= 255.0! c+ H  U. V, i/ S4 ~+ X

    + A9 c& Y- u& ~+ H: |% i

    0 o! m( A. I1 a        # annotation file
    1 q( _; N+ L, y* u8 B  `        annot_filename = img_name[:-4] + '.xml', n7 E3 X- x% K/ C# B' H" L! {
            annot_file_path = os.path.join(self.xml_dir, annot_filename)
    3 m$ g7 k/ m1 w; }8 p3 }7 L. h
      G  d8 @! L) Z/ C4 {) I
    + c+ f' I. i! C3 r8 ]  x# }
            boxes = []5 F. t$ ?) h8 [( _" a6 B
            labels = []& _* P" l' a+ W2 U8 E( c
            tree = et.parse(annot_file_path)
    ( D; Y: C7 A) ~/ C8 Y- {0 k$ l! j        root = tree.getroot()2 @( g7 U: W: {6 u
    : V; p2 `! U) E- h5 f. a3 ?" v

    ( l. W9 W1 ?2 N. C% a5 ~        # cv2 image gives size as height x width4 |4 P, d, X; C# ^8 R1 ?" ^
            wt = img.shape[1]
      Y% x  O" V$ z0 y' R        ht = img.shape[0]
    & n( T7 `3 ~% A% i9 K# Q4 Z
    6 H0 f2 u( [- M7 [, C" _( m: a

      M! D3 x1 a. _: I. J% l        # box coordinates for xml files are extracted and corrected for image size given
    8 t& @' w: c  H1 ~$ k. F( @) Z, i        for member in root.findall('object'):
    * U) e7 A3 j3 X: b            labels.append(self.classes.index(member.find('name').text))
    6 U* j0 g: M1 _4 j  }
    0 z; i4 R1 b. V! t

    # E( ^# |, v" L/ J            # bounding box, X' v% |, g( J
                xmin = int(member.find('bndbox').find('xmin').text)4 l' o* k, m8 v; k6 L# v
                xmax = int(member.find('bndbox').find('xmax').text)
    8 {0 ]" ^- }4 {7 ?# t7 N' G2 t8 M7 [9 s

    , |4 M# R: S: u0 [            ymin = int(member.find('bndbox').find('ymin').text)- {1 e) R4 E1 l5 v# j. W- J9 m
                ymax = int(member.find('bndbox').find('ymax').text)3 z: q! Q; I9 r- p$ z$ G2 l- v, R7 P
    0 o; r  T0 t  k9 e8 h4 i* o
    / a* ^: H6 T5 F: ?: K' l0 f
                xmin_corr = (xmin / wt) * self.width2 R+ F4 ]: r3 p
                xmax_corr = (xmax / wt) * self.width$ I- s0 o. `+ E" `
                ymin_corr = (ymin / ht) * self.height
    & ~7 }8 T6 \1 X% w2 Z            ymax_corr = (ymax / ht) * self.height, C, O2 Z! }$ u
                boxes.append([xmin_corr, ymin_corr, xmax_corr, ymax_corr])
    1 Q7 h2 F7 T5 }) L
    1 c: ], Y( t: ?8 e, [$ o, \
    ( `  ]. a; O& \
            # convert boxes into a torch.Tensor6 n; ]9 X( \7 E- r; Y5 v5 L! I
            boxes = torch.as_tensor(boxes, dtype=torch.float32)
    5 _3 q9 v& o- C8 ?5 {  o
    7 p2 k) g9 L/ c7 Z
    % M5 T( V) M7 y: U$ h
            # getting the areas of the boxes
    2 D6 f- {! s2 F6 S, n) c        area = (boxes[:, 3] - boxes[:, 1]) * (boxes[:, 2] - boxes[:, 0])
    0 W8 \/ f9 i2 o  S) b. e9 U7 F, F- M$ ?2 c1 S# H

    5 V% D5 ?1 y, m/ K3 A7 A& ~( \  P        # suppose all instances are not crowd
    8 H( r/ w! L: F; }        iscrowd = torch.zeros((boxes.shape[0],), dtype=torch.int64)( m; i+ S1 V% D' `  z) @" i1 [
    - p" L+ h. e7 O5 F; {. B7 |

    , R5 [+ r( l6 h( s! ]6 N8 G        labels = torch.as_tensor(labels, dtype=torch.int64)
    % E7 U7 ]4 S8 i
    3 |; ?; B. o5 g- d8 _7 ~: v4 ^" s0 b

    6 D, }" l$ R! ]/ o, E        target = {}) d. C# [" A( `# g
            target["boxes"] = boxes
    . _; a- H" N4 E, S. G9 \        target["labels"] = labels2 S, B; I0 h4 D  Y2 D9 [7 C
            target["area"] = area
    * A% X, b+ V% W- C6 G        target["iscrowd"] = iscrowd
    & |/ Z4 ?& w; J) b3 [+ P        # image_id% S4 z+ X' ?* L4 R
            image_id = torch.tensor([idx])
    $ K$ H% m$ l) ~, r5 \        target["image_id"] = image_id8 s; P$ b6 R) x  l6 q' H  P

    - R# v$ V. e8 k/ X8 q) h
    / i" x- m7 f  n% c! M* y
            if self.transforms:) O( ?) @/ e/ W2 Y
                sample = self.transforms(image=img_res,
    1 v) u8 z$ s  n6 J: _5 y                                     bboxes=target['boxes'],( `. _! \+ @. x6 _
                                         labels=labels)% e, O9 P7 h% V  I% G6 J4 g6 S" S
    3 S0 U+ [/ M" \# s
    - F# w; B+ \) ?  B' c
                img_res = sample['image']/ V, K! x/ M* e. ]& m$ Y, A
                target['boxes'] = torch.Tensor(sample['bboxes'])
    ' r& u/ u  U8 I  P- z: Y) ]0 a4 d4 ?/ c) y! E! L4 S

    0 i# A# J+ T0 p: Z        return img_res, target7 k9 ~7 }2 T7 _2 l& J4 g$ k+ J
      f* I* d/ @8 n5 |; n( x
    . E% r0 y. X2 ?3 _8 l! R$ F' v
        def __len__(self):
    & I+ r* `( c0 z1 F        return len(self.imgs)
    1 Q9 r7 D: g, q) K& b0 f2 _2 D5 w( v' J! n
    & y* P2 Q. N: |6 `, x
    # function to convert a torchtensor back to PIL image
    1 ]/ ?7 N3 d/ Udef torch_to_pil(img):
    : k' x: O. P) n$ x& k# l: G    return torchtrans.ToPILImage()(img).convert('RGB')5 b: M8 ]% E5 W8 a8 e% t
    $ \1 G: d# }  d: ]5 F* B

    % f( P8 m# R8 G& C
    : l% b2 ?% G7 J. w

    6 R8 c- }3 s/ S1 w2 g7 ?def plot_img_bbox(img, target):" s3 b; M# p+ _
        # plot the image and bboxes! }5 S# r' M& Z4 n( {" f
        fig, a = plt.subplots(1, 1)
    / v" t! A0 E3 d) A$ y2 M+ u    fig.set_size_inches(5, 5). {4 @. u3 U0 K4 h: ~
        a.imshow(img)
    ) l8 M' i9 _& f    for box in (target['boxes']):
    ! N  H8 b% r; O3 d        x, y, width, height = box[0], box[1], box[2] - box[0], box[3] - box[1]
    / q( k  b1 `. l& j% s4 c5 R% y" X1 I        rect = patches.Rectangle((x, y),6 Z# }4 s- q1 b4 i5 y/ ]
                                     width, height,
    / h( W9 I) s" [" s" q5 r8 B                                 linewidth=2,
    - s& b, W1 r4 C% y: |, l( s. z6 h                                 edgecolor='r',- r/ Y8 k, M( ^  k4 C* T9 x
                                     facecolor='none')
    ; e( w" X; k" Z$ J
    3 M$ o( y- o1 U$ T- c" K
    ' a. }0 Y- ]$ F5 Q+ A! N
            # Draw the bounding box on top of the image8 q) P- T" G9 \  R  X" F, }3 U' y/ x
            a.add_patch(rect)
    $ S- p! `4 u7 }2 ]+ @  P) c: o" F+ {    plt.show()
    7 R2 A% a7 ^  _; q
    ( C" y- W) D% q- J5 n" z, c2 W! @
    ! F! ?* w3 \) m' G. w- o
    / n" v# E% a0 t- T- c
    ' d2 S) Y. m6 |, V9 ]
    def get_transform(train):7 P% h; }7 @1 O' l( W
        if train:
    1 s! x$ x0 k+ {3 [9 @( p+ M# S" T. x        return A.Compose([8 v2 {/ v/ ~; a- Y& u+ W! v
                A.HorizontalFlip(0.5),9 ?, t" @3 n( U
                # ToTensorV2 converts image to pytorch tensor without div by 255
    , D  X$ Y% Y4 E1 q4 z4 B4 r' i' ~/ d            ToTensorV2(p=1.0)
    7 s0 f8 B6 H! b' ]        ], bbox_params={'format': 'pascal_voc', 'label_fields': ['labels']}), W# H; O3 v1 U- {3 E  C0 F
        else:
    1 q0 o- L5 p, j5 v2 }5 h5 e  r        return A.Compose([
    : |) @+ f2 Y2 w            ToTensorV2(p=1.0)5 S3 j6 G& Q$ i3 A/ i7 N
            ], bbox_params={'format': 'pascal_voc', 'label_fields': ['labels']})
    - E& e: M  ]/ T4 j/ o. p/ D
    # V# H/ A. C6 |& l7 d+ s
    5 \! O) z" p2 r5 C9 \
    $ |+ {, R) M3 R: T) ~. `
      x6 z+ F7 X, o0 C$ l
    2 W% Z4 I! F5 ~1 s1 m- k2 _- j

    3 e4 r9 K  I" m" ~& D  ~  t/ fdataset = FruitImagesDataset(train_image_dir,train_xml_dir, 480, 480, transforms= get_transform(train=True))
    ) O6 ^% V6 H2 h, Q1 j1 b$ R/ g& Z( f9 P/ u* t; \) P! s( Y

    + v( C2 W: ]+ n: W" W5 Bprint(len(dataset))% p7 M2 I7 i* n) f
    # getting the image and target for a test index.  Feel free to change the index.1 t( ~' {8 o% b8 z5 y4 g
    img, target = dataset[29]7 o/ e* \6 p3 z5 l/ o
    print(img.shape, '\n', target)
    ( f" r' I; X9 S6 x  y* x) Rplot_img_bbox(torch_to_pil(img), target)
    " ?2 P9 ]4 {5 e, [9 z2 e- l: C15 j7 t9 \2 G* X
    2
      ~8 J- L: h0 W3. A! w3 @3 R# d7 p9 R  ]
    4
    8 d( |! `# J1 b6 @5
    - I# G8 @' E6 E* j6) T" H8 Y! d" m0 t; O) t4 w$ R8 a
    7
    * E! ]6 W+ z5 E) h1 v$ C- f89 r, s; S3 z% l
    9
    : J" p4 I5 P+ c) G" A10
    + O) `  o& w1 v: H( E5 o9 G11
    $ g0 s  N6 ^, h* U2 r! q. Y" F- R12
      T) j1 s, r& v* h4 O13
    , V7 F5 ^7 `+ O. q, [3 T1 w14
    1 W7 f( b- p4 J7 v15; F3 J9 ]: B2 R2 Z
    16; h( t: y- P4 z  `: X+ _) R
    17
    ! }# |! ?& _  D1 H$ N+ o* ^, @18
    ' H. _1 g& X/ F; W: ]* X+ u19% j) x5 X! [+ e5 `$ p; |
    20
    9 Y& D; V2 g/ M2 L# W0 O6 T21$ O+ l* \( W4 x* s$ \1 J% `
    22
    9 n+ J2 ]/ t4 v: f( H3 [237 n. n4 {' @: s; x& V  T( [
    24- T3 W( j3 a! }* J# U" T- \' C
    25
    2 b5 H6 r/ F! v! d3 j2 k26
    0 j6 W0 `9 b2 j' u5 r5 d27
    $ T% M" {' t$ q$ L3 f& N6 X28
    - |$ T0 ~4 A/ r" H29
    ' O% o& \) p6 Y8 x7 K) @' L; ]300 j2 ?5 Y1 O# E0 x) l
    319 S% N6 D. ~9 y8 m7 j
    32
      X. `  d7 u( i+ O  ?33
    ; G. X7 i  \' O3 @4 {34
    ! E( V( e/ M! b5 T6 I8 _- O! f% |350 f; J% h4 S$ X, K/ U5 O
    361 d7 r& t  C; V* ~* \( W
    37# G& a- D" x7 H8 W
    386 g: @  [: `" L* U6 S  e
    39# w7 M+ _2 q6 g. F
    403 G- V3 z0 I3 R# g3 k0 F
    41
    7 H' `. e6 I" ]% M- L+ ~8 r42
    / ~6 m7 l6 D0 w$ K  U43# v) p3 c, D8 n" x1 Q6 J
    44
    9 i; ]1 b; d$ `) J45- V+ K* d7 \/ G% t
    46+ U6 t4 a$ h0 O6 h
    47
    " [, x, I  }" P( B3 h485 i+ j/ ?8 Y* W4 P% q* e
    49: _0 V5 x8 B" ~" [% z" i- Q
    50
    4 P' p; E) i" X# R+ q51
    9 _) H( @+ T$ M7 ?4 f& h' V: _520 k0 [" n" b5 R4 b  }3 c/ k+ J
    53$ v( T0 U) n/ Y/ Z, U- P2 v
    549 q7 W( S9 L. G1 F& u, L4 T
    55) V0 r. {- b* _: S; u/ |* U) E: S
    56
    0 N: B' w5 n4 X4 ^57
    + ~/ n. c+ V) Z2 N' H5 _8 W5 d7 E58
    8 P6 D& z4 v' U, \" q% r; E' G59
    ' x2 u6 v5 M( [: P. C8 P601 W0 F8 T! B% u/ y% J4 m" q
    613 F. N/ n0 M( J1 Y, ^. ]
    62
    % J: P) w8 ~) |; ]% l; Q" M6 C' L639 e# R" m; F/ |  O# C! ?& P* y* J
    64. w% v8 {7 j5 A3 m8 I+ U+ \6 U
    65, R$ {$ w$ J* D" Y$ ^/ v  j0 s% z
    66
    . m: C3 J! W6 Q4 G3 J% _67' _: ~3 p8 {, g0 l
    68+ c( b9 `3 C5 t
    69
    8 p2 k" \) c4 f& d9 [70$ n% E+ N: l# ?  U( {: y7 ^" G
    71
    4 R+ c8 z) g9 V' m3 _9 |! j72& H5 j. T2 r7 I9 C; s
    73. J$ S# S/ u& M7 z0 d, }3 o5 Y* F
    741 X( |+ a" X+ B0 D4 w! ^
    754 R$ `3 a: d; ~, a0 f
    76
    7 L; N3 B9 x. d6 \  f2 d/ d! b778 X, Y" M1 ~( l3 G& w
    78
    % @3 z& w* ^) L$ d79
    2 C7 E8 x8 h" K% J$ Z8 `  K80
    2 h, \2 X: c- i$ A+ B. x81
    3 G: R8 P* B, }0 q3 A  U) t82
    - e3 \/ L7 z% Y" A/ `83) B6 ^8 F; o9 z, C* K, n9 k- Y+ B- e
    843 \* a! b: k; a
    853 _, X+ M- E4 f  r( _
    868 z( x5 t- o9 Q/ w0 G. x
    87+ @0 S  q6 g( T/ n% b; X
    88+ k6 U+ T- y$ C# }0 P' i3 k5 D
    89
    " I1 j- D9 V1 C1 a6 J2 r9 A: i90
    $ `) |0 W: _0 b- |- V! u4 D91
    , Z& U3 m* s  r0 K8 Q& R92
    5 K) S/ w1 H  G$ X7 U939 G7 i" q4 r7 I$ K3 e6 `
    94
    5 `  `  s" I: _8 W0 @95
      x$ v; c1 `/ d2 ~9 T/ r5 w961 B. F* n. {* c
    979 u* B" e8 W1 ?5 m' J! Q
    98
    : K- D+ H9 {) \% m, I% d  u994 M; u& m8 l! |/ g" C9 R- s( _
    1002 A& L5 b$ J& F/ Y
    101* a8 ?( `$ w9 c
    102, v3 h4 |/ {  i9 x0 i* E
    103: L. L- F: e) e; f; g
    104
    7 M3 E6 @8 g5 }/ W. K2 p  ?105+ w- R+ ~- @* E3 z
    106
    6 Q4 H' t2 ^+ n1 C107
    : ?1 }6 G8 O6 G108
    * s. a+ d: s, O; ~109
    6 `3 }: o2 V) B" t" |9 h# K110- p8 {3 j( O- K4 ?$ `
    111
    3 j( g7 K, I- |1 Z' G- b112
    4 O0 E6 P6 L8 j# `1137 i) b3 e( K# T
    114
      }# h4 l3 y# ]115
    % i% m( w7 A$ F% Y) D/ [116! u/ K5 d' w8 a
    1172 L% g0 `9 K+ P  \5 F- f
    118
    : W( m  `$ `1 h# V119& U; N  E0 V9 ]  |6 u/ U0 W1 r
    120
    + H9 |( k0 Y1 \121+ Z! |: a' @( l
    122
    - j& o3 T. o) f, F9 Z- X123
    8 d3 o) p) l2 ]) e- `8 _124
    1 a& m7 q$ p8 {! z. t1256 v! S' c/ ^; I2 t6 r  T
    126. p& \0 M3 T  e0 |& G1 h. ~; A  q
    127
    + |! Y4 I  z8 g& }: h6 Z128; T& ^; s2 Q* n' ~! B
    129* g6 b& ~! ~0 ?
    130
    8 @5 W" t( j) J; N4 S$ G7 _) N131
    - l2 ]' [6 ]* y2 {  F132
    3 a, u5 C1 S* B133& n4 `0 J# \& v+ f, ~! y1 }
    134
    ( ]4 A+ x! y- `6 M4 @135+ i& H+ L9 D+ p9 ^
    1362 H' ?8 X9 {) S7 {6 ?2 p5 D& `/ ]
    137
    2 ]6 z9 P9 f" ]7 n) m' \138# {+ r* c! _- a, O: X
    139
    . Q" ]3 q9 c7 S" a# {$ O# w1400 M8 B9 A( H) N! C! b
    1416 b1 g; u' N6 j* i- r6 N
    142
    9 u. p. a; x: O. b- t$ N" n143- C4 d; E( |, ]1 G" @. \5 w
    144, ^2 Z( e2 v6 e6 c+ d
    145! @9 \: ]$ g2 q
    146
    : x# t5 s! q6 [* D147
      _2 g+ _, O& S: X) ^148
    & `0 g  l8 b1 e1 _149
    , J4 v" x5 V9 D) {+ D8 [' ^150/ g2 P4 F9 D' _3 k0 a, B
    151$ m3 C6 P* L5 c& L8 ?
    1527 A9 h% X4 x! @$ |) e
    153, O7 a# |/ I6 a
    154
    " n- S) L) n& b$ s' C. p155& [. _; z- b& F) ?$ l
    156' ?) [4 P5 c1 w% O. D, f5 Z
    输出如下:
    6 G( t# Y3 s  h: c5 c, B- A. j8 E# U/ \3 S/ M: B. g

    . X6 N5 t5 F) Y5 m+ ]torch.Size([3, 480, 480])
    8 V. f6 n1 }) U2 p1 z {'boxes': tensor([[130.8000,  97.8000, 327.6000, 292.2000],5 g- E& M/ u7 b1 H  Z! @6 D
            [159.0000, 268.8000, 349.8000, 427.8000],
    1 y9 M5 t* U; F3 `/ z. g& q' q        [  0.0000, 282.0000, 118.2000, 429.6000],
    ( d7 t* v6 I9 c, f/ S        [ 43.8000, 107.4000, 199.2000, 280.2000],
    ! A' G4 w# ]/ Y! `( N        [295.2000,  37.8000, 479.4000, 248.4000]]), 'labels': tensor([0, 0, 0, 0, 0]), 'area': tensor([38257.9258, 30337.2012, 17446.3223, 26853.1270, 38792.5195]), 'iscrowd': tensor([0, 0, 0, 0, 0]), 'image_id': tensor([29])}
    & Q/ K, k6 H9 }4 I1
    + o2 U& |. z: X# R2
    / w3 Q$ D) S( M9 {  _; U6 H4 F% Z3
    1 q7 w. y2 k, V: H0 l' O+ n4
      C2 v0 l$ |% O* L5% t# ~1 L0 B* A
    6
    ' M. A  _+ j/ Z1 O% {: m. C# E& w! ]; q! y9 B' Q1 B' T9 S

    1 E. F7 p0 a6 j! o1 L* p2 R
    ! I5 ~- n  n) x- D' E
    . K$ j' W7 a! K; h1 b
    下载地址
    4 n; f  T& u1 w# c' g链接:https://pan.baidu.com/s/1QZDgeYTHyAlD2xhtJqZ-Yw: b, @  `2 N, b! u
    提取码:srjn
    - T0 R+ N# O; C. U+ N1 L# v0 K( U————————————————: z: [8 E# c# g0 {1 B0 J
    版权声明:本文为CSDN博主「刘润森!」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。: V, L5 {" {- w: M4 h
    原文链接:https://blog.csdn.net/weixin_44510615/article/details/118496273
    3 V6 K+ D$ Z1 i3 [  e
    4 h' J5 ]& T; O" I1 P% K4 C. J! z  H3 d* N5 t  c6 e" e
    zan
    转播转播0 分享淘帖0 分享分享0 收藏收藏0 支持支持0 反对反对0 微信微信
    您需要登录后才可以回帖 登录 | 注册地址

    qq
    收缩
    • 电话咨询

    • 04714969085
    fastpost

    关于我们| 联系我们| 诚征英才| 对外合作| 产品服务| QQ

    手机版|Archiver| |繁體中文 手机客户端  

    蒙公网安备 15010502000194号

    Powered by Discuz! X2.5   © 2001-2013 数学建模网-数学中国 ( 蒙ICP备14002410号-3 蒙BBS备-0002号 )     论坛法律顾问:王兆丰

    GMT+8, 2026-5-26 16:45 , Processed in 0.469380 second(s), 51 queries .

    回顶部