"docs_zh_CN/git@developer.sourcefind.cn:OpenDAS/mmcv.git" did not exist on "8d2d78122538056d3ab60a6533abb2c8be45516c"
Commit d31aba8a authored by Kaushik Shivakumar's avatar Kaushik Shivakumar
Browse files

using already pushed files

parent 245e9d16
......@@ -303,6 +303,7 @@ def iou(boxlist1, boxlist2, scope=None):
tf.equal(intersections, 0.0),
tf.zeros_like(intersections), tf.truediv(intersections, unions))
def l1(boxlist1, boxlist2, scope=None):
"""Computes l1 loss (pairwise) between two boxlists.
......@@ -317,21 +318,20 @@ def l1(boxlist1, boxlist2, scope=None):
with tf.name_scope(scope, 'PairwiseL1'):
ycenter1, xcenter1, h1, w1 = boxlist1.get_center_coordinates_and_sizes()
ycenter2, xcenter2, h2, w2 = boxlist2.get_center_coordinates_and_sizes()
ycenters = tf.abs(tf.expand_dims(ycenter2, axis=0) - \
tf.expand_dims(tf.transpose(ycenter1), axis=1))
xcenters = tf.abs(tf.expand_dims(xcenter2, axis=0) - \
tf.expand_dims(tf.transpose(xcenter1), axis=1))
heights = tf.abs(tf.expand_dims(h2, axis=0) - \
tf.expand_dims(tf.transpose(h1), axis=1))
widths = tf.abs(tf.expand_dims(w2, axis=0) - \
tf.expand_dims(tf.transpose(w1), axis=1))
ycenters = tf.abs(tf.expand_dims(ycenter2, axis=0) - tf.expand_dims(
tf.transpose(ycenter1), axis=1))
xcenters = tf.abs(tf.expand_dims(xcenter2, axis=0) - tf.expand_dims(
tf.transpose(xcenter1), axis=1))
heights = tf.abs(tf.expand_dims(h2, axis=0) - tf.expand_dims(
tf.transpose(h1), axis=1))
widths = tf.abs(tf.expand_dims(w2, axis=0) - tf.expand_dims(
tf.transpose(w1), axis=1))
return ycenters + xcenters + heights + widths
def giou_loss(boxlist1, boxlist2, scope=None):
"""
Computes generalized IOU loss between two boxlists pairwise,
as described at giou.stanford.edu.
def giou(boxlist1, boxlist2, scope=None):
"""Computes pairwise generalized IOU between two boxlists.
Args:
boxlist1: BoxList holding N boxes
boxlist2: BoxList holding M boxes
......@@ -340,12 +340,13 @@ def giou_loss(boxlist1, boxlist2, scope=None):
Returns:
a tensor with shape [N, M] representing the pairwise GIoU loss.
"""
with tf.name_scope(scope, "PairwiseGIoU"):
N = boxlist1.num_boxes()
M = boxlist2.num_boxes()
boxes1 = tf.repeat(boxlist1.get(), repeats=M, axis=0)
boxes2 = tf.tile(boxlist2.get(), multiples=[N, 1])
return tf.reshape(1.0 - ops.giou(boxes1, boxes2), [N, M])
with tf.name_scope(scope, 'PairwiseGIoU'):
n = boxlist1.num_boxes()
m = boxlist2.num_boxes()
boxes1 = tf.repeat(boxlist1.get(), repeats=m, axis=0)
boxes2 = tf.tile(boxlist2.get(), multiples=[n, 1])
return tf.reshape(ops.giou(boxes1, boxes2), [n, m])
def matched_iou(boxlist1, boxlist2, scope=None):
"""Compute intersection-over-union between corresponding boxes in boxlists.
......@@ -367,6 +368,7 @@ def matched_iou(boxlist1, boxlist2, scope=None):
tf.equal(intersections, 0.0),
tf.zeros_like(intersections), tf.truediv(intersections, unions))
def ioa(boxlist1, boxlist2, scope=None):
"""Computes pairwise intersection-over-area between box collections.
......
......@@ -217,6 +217,7 @@ class BoxListOpsTest(test_case.TestCase):
def test_iou(self):
def graph_fn():
corners1 = tf.constant([[4.0, 3.0, 7.0, 5.0], [5.0, 6.0, 10.0, 7.0]])
corners1 = tf.constant([[4.0, 3.0, 7.0, 5.0], [5.0, 6.0, 10.0, 7.0]])
corners2 = tf.constant([[3.0, 4.0, 6.0, 8.0], [14.0, 14.0, 15.0, 15.0],
[0.0, 0.0, 20.0, 20.0]])
......@@ -247,9 +248,9 @@ class BoxListOpsTest(test_case.TestCase):
corners2 = tf.constant([[5.0, 7.0, 7.0, 9.0], [5.0, 11.0, 7.0, 13.0]])
boxes1 = box_list.BoxList(corners1)
boxes2 = box_list.BoxList(corners2)
giou = box_list_ops.giou_loss(boxes1, boxes2)
giou = box_list_ops.giou(boxes1, boxes2)
return giou
exp_output = [[0.0, 4.0 / 3.0]]
exp_output = [[1.0, -1.0 / 3.0]]
giou_output = self.execute(graph_fn, [])
self.assertAllClose(giou_output, exp_output)
......
......@@ -211,12 +211,11 @@ class WeightedIOULocalizationLoss(Loss):
return tf.reshape(weights, [-1]) * per_anchor_iou_loss
class WeightedGIOULocalizationLoss(Loss):
"""IOU localization loss function.
"""GIOU localization loss function.
Sums the IOU for corresponding pairs of predicted/groundtruth boxes
and for each pair assign a loss of 1 - IOU. We then compute a weighted
Sums the GIOU loss for corresponding pairs of predicted/groundtruth boxes
and for each pair assign a loss of 1 - GIOU. We then compute a weighted
sum over all pairs which is returned as the total loss.
"""
......
......@@ -197,6 +197,7 @@ class WeightedIOULocalizationLossTest(test_case.TestCase):
loss_output = self.execute(graph_fn, [])
self.assertAllClose(loss_output, exp_loss)
class WeightedGIOULocalizationLossTest(test_case.TestCase):
def testReturnsCorrectLoss(self):
......
......@@ -15,21 +15,16 @@
"""Hungarian bipartite matcher implementation."""
import tensorflow.compat.v1 as tf
import numpy as np
from scipy.optimize import linear_sum_assignment
import tensorflow.compat.v1 as tf
from object_detection.core import matcher
from scipy.optimize import linear_sum_assignment
class HungarianBipartiteMatcher(matcher.Matcher):
"""Wraps a Hungarian bipartite matcher into TensorFlow."""
def __init__(self):
"""Constructs a Matcher."""
super(HungarianBipartiteMatcher, self).__init__()
def _match(self, similarity_matrix, valid_rows):
"""Optimally bipartite matches a collection rows and columns.
......
# Copyright 2017 The TensorFlow Authors. All Rights Reserved.
# Copyright 2020 The TensorFlow Authors. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
......@@ -100,5 +100,6 @@ class HungarianBipartiteMatcherTest(test_case.TestCase):
self.assertAllEqual(match_results_out._match_results.numpy(),
expected_match_results)
if __name__ == '__main__':
tf.test.main()
......@@ -216,13 +216,13 @@ def pad_to_multiple(tensor, multiple):
height_pad = tf.zeros([
batch_size, padded_tensor_height - tensor_height, tensor_width,
tensor_depth
])
], dtype=tensor.dtype)
tensor = tf.concat([tensor, height_pad], 1)
if padded_tensor_width != tensor_width:
width_pad = tf.zeros([
batch_size, padded_tensor_height, padded_tensor_width - tensor_width,
tensor_depth
])
], dtype=tensor.dtype)
tensor = tf.concat([tensor, width_pad], 2)
return tensor
......@@ -1135,10 +1135,11 @@ def decode_image(tensor_dict):
tensor_dict[fields.InputDataFields.image].set_shape([None, None, 3])
return tensor_dict
def giou(boxes1, boxes2):
"""
Computes generalized IOU between two tensors. Each box should be
represented as [ymin, xmin, ymax, xmax].
"""Computes generalized IOU between two tensors.
Each box should be represented as [ymin, xmin, ymax, xmax].
Args:
boxes1: a tensor with shape [num_boxes, 4]
......@@ -1146,46 +1147,43 @@ def giou(boxes1, boxes2):
Returns:
a tensor of shape [num_boxes] containing GIoUs
"""
def two_boxes_giou(boxes):
def _two_boxes_giou(boxes):
"""Compute giou between two boxes."""
boxes1, boxes2 = boxes
pred_ymin = tf.gather_nd(boxes1, [0])
pred_xmin = tf.gather_nd(boxes1, [1])
pred_ymax = tf.gather_nd(boxes1, [2])
pred_xmax = tf.gather_nd(boxes1, [3])
gt_ymin = tf.gather_nd(boxes2, [0])
gt_xmin = tf.gather_nd(boxes2, [1])
gt_ymax = tf.gather_nd(boxes2, [2])
gt_xmax = tf.gather_nd(boxes2, [3])
pred_ymin, pred_xmin, pred_ymax, pred_xmax = tf.unstack(boxes1)
gt_ymin, gt_xmin, gt_ymax, gt_xmax = tf.unstack(boxes2)
gt_area = (gt_ymax - gt_ymin) * (gt_xmax - gt_xmin)
pred_area = (pred_ymax - pred_ymin) * (pred_xmax - pred_xmin)
x1I = tf.maximum(pred_xmin, gt_xmin)
x2I = tf.minimum(pred_xmax, gt_xmax)
y1I = tf.maximum(pred_ymin, gt_ymin)
y2I = tf.minimum(pred_ymax, gt_ymax)
intersection_area = (y2I - y1I) * (x2I - x1I) if (y2I > y1I and
x2I > x1I) else 0.0
x1_i = tf.maximum(pred_xmin, gt_xmin)
x2_i = tf.minimum(pred_xmax, gt_xmax)
y1_i = tf.maximum(pred_ymin, gt_ymin)
y2_i = tf.minimum(pred_ymax, gt_ymax)
intersection_area = tf.maximum(0.0, y2_i - y1_i) * tf.maximum(0.0,
x2_i - x1_i)
x1C = tf.minimum(pred_xmin, gt_xmin)
x2C = tf.maximum(pred_xmax, gt_xmax)
y1C = tf.minimum(pred_ymin, gt_ymin)
y2C = tf.maximum(pred_ymax, gt_ymax)
hull_area = (y2C - y1C) * (x2C - x1C)
x1_c = tf.minimum(pred_xmin, gt_xmin)
x2_c = tf.maximum(pred_xmax, gt_xmax)
y1_c = tf.minimum(pred_ymin, gt_ymin)
y2_c = tf.maximum(pred_ymax, gt_ymax)
hull_area = (y2_c - y1_c) * (x2_c - x1_c)
union_area = gt_area + pred_area - intersection_area
IoU = intersection_area/union_area if union_area != 0.0 else 1.0
gIoU = IoU - (hull_area - union_area) / hull_area if hull_area != 0.0 else IoU
iou = tf.where(
tf.equal(union_area, 0.0), 0.0, intersection_area / union_area)
giou_ = iou - tf.where(hull_area > 0.0,
(hull_area - union_area) / hull_area, iou)
return giou_
return gIoU
return shape_utils.static_or_dynamic_map_fn(_two_boxes_giou, [boxes1, boxes2])
return shape_utils.static_or_dynamic_map_fn(two_boxes_giou, [boxes1, boxes2])
def cy_cx_h_w_to_ymin_xmin_ymax_xmax(input_tensor):
def center_to_corner_coordinate(input_tensor):
"""Converts input boxes from center to corner representation."""
reshaped_encodings = tf.reshape(input_tensor, [-1, 4])
ycenter = tf.gather(reshaped_encodings, [0], axis=1)
......@@ -1196,4 +1194,4 @@ def cy_cx_h_w_to_ymin_xmin_ymax_xmax(input_tensor):
xmin = xcenter - w / 2.
ymax = ycenter + h / 2.
xmax = xcenter + w / 2.
return tf.squeeze(tf.stack([ymin, xmin, ymax, xmax], axis=1))
\ No newline at end of file
return tf.squeeze(tf.stack([ymin, xmin, ymax, xmax], axis=1))
......@@ -1630,20 +1630,95 @@ class TestGatherWithPaddingValues(test_case.TestCase):
self.assertAllClose(expected_gathered_tensor, gathered_tensor_np)
class TestGIoU(test_case.TestCase):
def test_giou(self):
def test_giou_with_no_overlap(self):
expected_giou_tensor = [
0, -1/3, -3/4, 0, -98/100
]
def graph_fn():
boxes1 = tf.constant([[3, 4, 5, 6], [3, 3, 5, 5],
[0, 0, 0, 0], [3, 3, 5, 5],
[9, 9, 10, 10]],
dtype=tf.float32)
boxes2 = tf.constant([[3, 2, 5, 4], [3, 7, 5, 9],
[5, 5, 10, 10], [3, 5, 5, 7],
[0, 0, 1, 1]], dtype=tf.float32)
giou = ops.giou(boxes1, boxes2)
self.assertEqual(giou.dtype, tf.float32)
return giou
giou = self.execute(graph_fn, [])
self.assertAllClose(expected_giou_tensor, giou)
def test_giou_with_overlaps(self):
expected_giou_tensor = [
1, 0, -1/3, 1/25, 1, -3/4
1/25, 1/4, 1/3, 1/7 - 2/9
]
def graph_fn():
boxes1 = tf.constant([[3, 3, 5, 5], [3, 4, 5, 6],
[3, 3, 5, 5], [2, 1, 7, 6],
[1, 1, 1, 1], [0, 0, 0, 0]], dtype=tf.float32)
boxes2 = tf.constant([[3, 3, 5, 5], [3, 2, 5, 4],
[3, 7, 5, 9], [4, 3, 5, 4],
[1, 1, 1, 1], [5, 5, 10, 10]], dtype=tf.float32)
boxes1 = tf.constant([[2, 1, 7, 6], [2, 2, 4, 4],
[2, 2, 4, 4], [2, 2, 4, 4]],
dtype=tf.float32)
boxes2 = tf.constant([[4, 3, 5, 4], [3, 3, 4, 4],
[2, 3, 4, 5], [3, 3, 5, 5]], dtype=tf.float32)
giou = ops.giou(boxes1, boxes2)
self.assertEqual(giou.dtype, tf.float32)
return giou
giou = self.execute(graph_fn, [])
self.assertAllClose(expected_giou_tensor, giou)
def test_giou_with_perfect_overlap(self):
expected_giou_tensor = [1]
def graph_fn():
boxes1 = tf.constant([[3, 3, 5, 5]], dtype=tf.float32)
boxes2 = tf.constant([[3, 3, 5, 5]], dtype=tf.float32)
giou = ops.giou(boxes1, boxes2)
self.assertEqual(giou.dtype, tf.float32)
return giou
giou = self.execute(graph_fn, [])
self.assertAllClose(expected_giou_tensor, giou)
def test_giou_with_zero_area_boxes(self):
expected_giou_tensor = [0]
def graph_fn():
boxes1 = tf.constant([[1, 1, 1, 1]], dtype=tf.float32)
boxes2 = tf.constant([[1, 1, 1, 1]], dtype=tf.float32)
giou = ops.giou(boxes1, boxes2)
self.assertEqual(giou.dtype, tf.float32)
return giou
giou = self.execute(graph_fn, [])
self.assertAllClose(expected_giou_tensor, giou)
def test_giou_different_with_l1_same(self):
expected_giou_tensor = [
2/3, 3/5
]
def graph_fn():
boxes1 = tf.constant([[3, 3, 5, 5], [3, 3, 5, 5]], dtype=tf.float32)
boxes2 = tf.constant([[3, 2.5, 5, 5.5], [3, 2.5, 5, 4.5]],
dtype=tf.float32)
giou = ops.giou(boxes1, boxes2)
self.assertEqual(giou.dtype, tf.float32)
......@@ -1658,13 +1733,14 @@ class TestCoordinateConversion(test_case.TestCase):
def test_coord_conv(self):
expected_box_tensor = [
[0.5, 0.5, 5.5, 5.5], [2, 1, 4, 7]
[0.5, 0.5, 5.5, 5.5], [2, 1, 4, 7], [0, 0, 0, 0]
]
def graph_fn():
boxes = tf.constant([[3, 3, 5, 5], [3, 4, 2, 6]], dtype=tf.float32)
boxes = tf.constant([[3, 3, 5, 5], [3, 4, 2, 6], [0, 0, 0, 0]],
dtype=tf.float32)
converted = ops.cy_cx_h_w_to_ymin_xmin_ymax_xmax(boxes)
converted = ops.center_to_corner_coordinate(boxes)
self.assertEqual(converted.dtype, tf.float32)
return converted
......@@ -1673,6 +1749,5 @@ class TestCoordinateConversion(test_case.TestCase):
self.assertAllClose(expected_box_tensor, converted)
if __name__ == '__main__':
tf.test.main()
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment