<?xml version="1.0" encoding="UTF-8"?>
<hdevelop file_version="1.1" halcon_version="13.0">
<procedure name="gradient_descent_bb">
<interface>
<io>
<par name="RegionSeg" base_type="iconic" dimension="0"/>
</io>
<oo>
<par name="Rectangle" base_type="iconic" dimension="0"/>
</oo>
<ic>
<par name="initial_box_coordinate" base_type="ctrl" dimension="0"/>
<par name="h" base_type="ctrl" dimension="0"/>
<par name="Display" base_type="ctrl" dimension="0"/>
<par name="WindowHandle" base_type="ctrl" dimension="0"/>
</ic>
<oc>
<par name="best_overlap" base_type="ctrl" dimension="0"/>
<par name="best_box_coordinate" base_type="ctrl" dimension="0"/>
</oc>
</interface>
<body>
<c> * Copyright (c) MVTec Software GmbH.  All rights reserved.</c>
<c> *</c>
<c> * All use of this software is subject to the terms of the revised BSD</c>
<c> * license.  You should have received a copy of this license along</c>
<c> * with this source code in a file named "license.txt."</c>
<c> </c>
<c>* Gradient descent parameters</c>
<l>    StepSize := 10.0</l>
<l>    tau := 0.8</l>
<l>    c := 0.8</l>
<l>    NumIter := 1000</l>
<c>    * We can only make as many inner iterations as</c>
<c>    * tau^x &gt; 1e-16 (else we're just wasting time...)</c>
<l>    NumIterInner := ceil(log(1e-16)/log(tau))</l>
<c>    *</c>
<l>    tuple_gen_const (NumIter, 0.0,Overlaps)</l>
<l>    region_bb_overlap (RegionSeg, initial_box_coordinate, overlap_initial)</l>
<l>    overlap := overlap_initial</l>
<l>    Overlaps[0] := overlap</l>
<l>    box_coordinate := initial_box_coordinate</l>
<c>    *</c>
<l>    overlap_old := overlap</l>
<c>    * Gradient descent iterations</c>
<l>    for Index := 1 to NumIter by 1</l>
<l>        gen_rectangle_b (Rectangle, box_coordinate)</l>
<c>        * overlap_bb == f(x)</c>
<l>        region_bb_overlap (RegionSeg, box_coordinate, overlap)</l>
<c>        </c>
<c>        * Define the gradient step. Setting a value to 0 prevents its optimization</c>
<l>        bb_overlap_gradient (RegionSeg, box_coordinate, h, grad)</l>
<c>            </c>
<c>        * Armijo-rule backtracking line search</c>
<l>        CurrentStepSize := StepSize</l>
<l>        mvtec_math_scalar_product (grad, grad, norm2)</l>
<l>        if (norm2 &lt; 1e-16)</l>
<c>            * Well well, the gradient is 0.0. Either we're optimal or</c>
<c>            * something has gone wrong (e.g. non overlapping regions)</c>
<l>            break</l>
<l>        endif</l>
<l>        p := grad/sqrt(norm2)</l>
<l>        m := sqrt(norm2)</l>
<l>        t := c*m</l>
<c>        *</c>
<c>        *</c>
<l>        for Iter := 1 to NumIterInner by 1</l>
<l>            box_coordinate_new := box_coordinate + CurrentStepSize * p</l>
<c>            * We need to ensure that b_new is within bounds</c>
<l>            box_coordinate_new[2:3] := [box_coordinate_new[2:3][&lt;]1.0]*1.0 + [box_coordinate_new[2:3][&gt;=]1.0]*box_coordinate_new[2:3]</l>
<l>            box_coordinate_new[2:3] := [box_coordinate_new[2:3][&lt;]1.0]*1.0 + [box_coordinate_new[2:3][&gt;=]1.0]*box_coordinate_new[2:3]</l>
<c>            *</c>
<l>            region_bb_overlap (RegionSeg, box_coordinate_new, best_overlap)</l>
<l>            CurrentStepSize := CurrentStepSize * tau</l>
<l>            if (best_overlap &gt; overlap + 0.0*(t*CurrentStepSize))</l>
<l>                break</l>
<l>            endif</l>
<l>*             box_coordinate_new := b + CurrentStepSize * grad</l>
<l>*             region_bb_overlap (RegionSeg, box_coordinate_new, best_overlap)</l>
<l>*             CurrentStepSize := CurrentStepSize * tau</l>
<l>*             if (best_overlap &gt; overlap + 0.0 * CurrentStepSize* norm2)</l>
<l>*                 break</l>
<l>*             endif</l>
<l>        endfor</l>
<c>    </c>
<c>        * Update b</c>
<l>        box_coordinate := box_coordinate_new</l>
<c>            </c>
<c>        * Remember the overlaps along the way</c>
<l>        gen_rectangle_b (Rectangle, box_coordinate)</l>
<l>        region_bb_overlap (RegionSeg, box_coordinate, overlap)</l>
<l>        Overlaps[Index] := overlap</l>
<c>        *</c>
<c>        ****************</c>
<c>        * Display</c>
<c>        **************** </c>
<l>        if (Display)</l>
<l>            set_system ('flush_graphic', 'false')</l>
<l>            dev_clear_window ()</l>
<l>            disp_region_alpha (RegionSeg, '#00ff00', 90)</l>
<l>            disp_region_alpha (Rectangle, '#ffff00', 90)</l>
<l>            set_system ('flush_graphic', 'true')</l>
<l>            disp_message (WindowHandle, 'bb_overlap: ' + overlap, 'window', 12, 12, 'black', 'true')</l>
<l>        endif</l>
<l>        if (abs(overlap_old-overlap) &lt;1e-16)</l>
<l>            break</l>
<l>        endif</l>
<l>        overlap_old := overlap</l>
<l>    endfor</l>
<l>best_box_coordinate := box_coordinate</l>
<l>best_overlap := overlap</l>
<l>return ()</l>
</body>
<docu id="gradient_descent_bb">
<parameters>
<parameter id="Display"/>
<parameter id="Rectangle"/>
<parameter id="RegionSeg"/>
<parameter id="WindowHandle"/>
<parameter id="best_box_coordinate"/>
<parameter id="best_overlap"/>
<parameter id="h"/>
<parameter id="initial_box_coordinate"/>
</parameters>
</docu>
</procedure>
</hdevelop>
