{"id":9337,"date":"2022-10-21T21:01:07","date_gmt":"2022-10-21T13:01:07","guid":{"rendered":"http:\/\/139.9.1.231\/?p=9337"},"modified":"2022-10-21T21:01:44","modified_gmt":"2022-10-21T13:01:44","slug":"pointnetplus","status":"publish","type":"post","link":"http:\/\/139.9.1.231\/index.php\/2022\/10\/21\/pointnetplus\/","title":{"rendered":"PointNet++"},"content":{"rendered":"\n<p class=\"has-light-pink-background-color has-background\">\u8bba\u6587\uff1a<a rel=\"noreferrer noopener\" href=\"https:\/\/arxiv.org\/abs\/1706.02413\" target=\"_blank\">https:\/\/arxiv.org\/abs\/1706.02413<\/a>\uff08NIPS 2017\uff09<\/p>\n\n\n\n<p class=\"has-light-gray-background-color has-background\">code\uff1a <a href=\"https:\/\/github.com\/charlesq34\/pointnet2\" target=\"_blank\" rel=\"noreferrer noopener\">https:\/\/github.com\/charlesq34\/pointnet2<\/a><\/p>\n\n\n\n<figure class=\"wp-block-image size-full is-resized\"><img loading=\"lazy\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-69.png\" alt=\"\" class=\"wp-image-9339\" width=\"690\" height=\"214\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-69.png 729w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-69-300x93.png 300w\" sizes=\"(max-width: 690px) 100vw, 690px\" \/><\/figure>\n\n\n\n\n\n<h2>1\u3001\u6539\u8fdb<\/h2>\n\n\n\n<p>       PointNet\u56e0\u4e3a\u662f\u53ea\u4f7f\u7528\u4e86MLP\u548cmax pooling\uff0c\u6ca1\u6709\u80fd\u529b\u6355\u83b7\u5c40\u90e8\u7ed3\u6784\uff0c\u56e0\u6b64\u5728\u7ec6\u8282\u5904\u7406\u548c\u6cdb\u5316\u5230\u590d\u6742\u573a\u666f\u4e0a\u80fd\u529b\u5f88\u6709\u9650\u3002<\/p>\n\n\n\n<ol><li>point-wise MLP\uff0c\u4ec5\u4ec5\u662f\u5bf9\u6bcf\u4e2a\u70b9\u8868\u5f81\uff0c\u5bf9\u5c40\u90e8\u7ed3\u6784\u4fe1\u606f\u6574\u5408\u80fd\u529b\u592a\u5f31 &#8211;&gt;&nbsp;<strong>PointNet++\u7684\u6539\u8fdb\uff1asampling\u548cgrouping\u6574\u5408\u5c40\u90e8\u90bb\u57df<\/strong><\/li><li><strong>global feature\u76f4\u63a5\u7531max pooling\u83b7\u5f97\uff0c\u65e0\u8bba\u662f\u5bf9\u5206\u7c7b\u8fd8\u662f\u5bf9\u5206\u5272\u4efb\u52a1\uff0c\u90fd\u4f1a\u9020\u6210\u5de8\u5927\u7684\u4fe1\u606f\u635f\u5931 <\/strong>&#8211;&gt;&nbsp;<strong>PointNet++\u7684\u6539\u8fdb\uff1ahierarchical feature learning framework\uff0c\u901a\u8fc7\u591a\u4e2aset abstraction\u9010\u7ea7\u964d\u91c7\u6837\uff0c\u83b7\u5f97\u4e0d\u540c\u89c4\u6a21\u4e0d\u540c\u5c42\u6b21\u7684local-global feature<\/strong><\/li><li>\u5206\u5272\u4efb\u52a1\u7684\u5168\u5c40\u7279\u5f81global feature\u662f\u76f4\u63a5\u590d\u5236\u4e0elocal feature\u62fc\u63a5\uff0c\u751f\u6210discriminative feature\u80fd\u529b\u6709\u9650 &#8211;&gt;&nbsp;<strong>PointNet++\u7684\u6539\u8fdb\uff1a\u5206\u5272\u4efb\u52a1\u8bbe\u8ba1\u4e86encoder-decoder\u7ed3\u6784\uff0c\u5148\u964d\u91c7\u6837\u518d\u4e0a\u91c7\u6837\uff0c\u4f7f\u7528skip connection\u5c06\u5bf9\u5e94\u5c42\u7684local-global feature\u62fc\u63a5<\/strong><\/li><\/ol>\n\n\n\n<h2>2\u3001\u65b9\u6cd5<\/h2>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" width=\"1024\" height=\"425\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-70-1024x425.png\" alt=\"\" class=\"wp-image-9354\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-70-1024x425.png 1024w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-70-300x124.png 300w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-70-768x318.png 768w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-70.png 1353w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><\/figure>\n\n\n\n<p class=\"has-text-align-center\">PointNet++\u7684\u7f51\u7edc\u5927\u4f53\u662fencoder-decoder\u7ed3\u6784<\/p>\n\n\n\n<p>             encoder\u4e3a\u964d\u91c7\u6837\u8fc7\u7a0b\uff0c\u901a\u8fc7\u591a\u4e2aset abstraction\u7ed3\u6784\u5b9e\u73b0\u591a\u5c42\u6b21\u7684\u964d\u91c7\u6837\uff0c\u5f97\u5230\u4e0d\u540c\u89c4\u6a21\u7684point-wise feature\uff0c\u6700\u540e\u4e00\u4e2aset abstraction\u8f93\u51fa\u53ef\u4ee5\u8ba4\u4e3a\u662fglobal feature\u3002\u5176\u4e2dset abstraction\u7531sampling\uff0cgrouping\uff0cpointnet\u4e09\u4e2a\u6a21\u5757\u6784\u6210\u3002<\/p>\n\n\n\n<p>             decoder\u6839\u636e\u5206\u7c7b\u548c\u5206\u5272\u5e94\u7528\uff0c\u53c8\u6709\u6240\u4e0d\u540c\u3002\u5206\u7c7b\u4efb\u52a1decoder\u6bd4\u8f83\u7b80\u5355\uff0c\u4e0d\u4ecb\u7ecd\u4e86\u3002\u5206\u5272\u4efb\u52a1decoder\u4e3a\u4e0a\u91c7\u6837\u8fc7\u7a0b\uff0c\u901a\u8fc7\u53cd\u5411\u63d2\u503c\u548cskip connection\u5b9e\u73b0\u5728\u4e0a\u91c7\u6837\u7684\u540c\u65f6\uff0c\u8fd8\u80fd\u591f\u83b7\u5f97local+global\u7684point-wise feature\uff0c\u4f7f\u5f97\u6700\u7ec8\u7684\u8868\u5f81\u80fd\u591fdiscriminative\uff08\u5206\u8fa9\u80fd\u529b\uff09\u3002<\/p>\n\n\n\n<p class=\"has-light-pink-background-color has-background\"><strong>\u601d\u8003\uff1a<\/strong><\/p>\n\n\n\n<ol><li>PointNet++\u964d\u91c7\u6837\u8fc7\u7a0b\u662f\u600e\u4e48\u5b9e\u73b0\u7684\uff1f\/PointNet++\u662f\u5982\u4f55\u8868\u5f81global feature\u7684\uff1f\uff08\u5173\u6ce8set abstraction, sampling layer, grouping layer, pointnet layer\uff09<\/li><li>PointNet++\u7528\u4e8e\u5206\u5272\u4efb\u52a1\u7684\u4e0a\u91c7\u6837\u8fc7\u7a0b\u662f\u600e\u4e48\u5b9e\u73b0\u7684\uff1f\/PointNet++\u662f\u5982\u4f55\u8868\u5f81\u7528\u4e8e\u5206\u5272\u4efb\u52a1\u7684point-wise feature\u7684\uff1f\uff08\u5173\u6ce8\u53cd\u5411\u63d2\u503c\uff0cskip connection\uff09<\/li><\/ol>\n\n\n\n<p class=\"has-bright-blue-background-color has-background\">&nbsp;\ud83d\udc16\uff1a\u4e0a\u56fe\u4e2d\u7684 <strong>d&nbsp;\u8868\u793a\u5750\u6807\u7a7a\u95f4\u7ef4\u5ea6\uff0c&nbsp;C&nbsp;\u8868\u793a\u7279\u5f81\u7a7a\u95f4\u7ef4\u5ea6<\/strong><\/p>\n\n\n\n<h3><strong>2.1 encoder<\/strong><\/h3>\n\n\n\n<p>         \u5728PointNet\u7684\u57fa\u7840\u4e0a\u589e\u52a0\u4e86hierarchical \uff08\u5c42\u7ea7\uff09feature learning framework\u7684\u7ed3\u6784\u3002\u8fd9\u79cd\u591a\u5c42\u6b21\u7684\u7ed3\u6784\u7531set abstraction\u5c42\u7ec4\u6210\u3002<\/p>\n\n\n\n<p>          \u5728\u6bcf\u4e00\u4e2a\u5c42\u6b21\u7684set abstraction\uff0c\u70b9\u96c6\u90fd\u4f1a\u88ab\u5904\u7406\u548c\u62bd\u8c61\uff0c\u800c\u4ea7\u751f\u4e00\u4e2a\u89c4\u6a21\u66f4\u5c0f\u7684\u70b9\u96c6\uff0c\u53ef\u4ee5\u7406\u89e3\u6210\u662f\u4e00\u4e2a\u964d\u91c7\u6837\u8868\u5f81\u8fc7\u7a0b\uff0c\u53ef\u53c2\u8003\u4e0a\u56fe\u5de6\u534a\u90e8\u5206\u3002<\/p>\n\n\n\n<p>set abstraction\u7531\u4e09\u4e2a\u90e8\u5206\u6784\u6210\uff08\u4ee3\u7801\u8d34\u5728\u4e0b\u9762\uff09\uff1a<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>def pointnet_sa_module(xyz, points, npoint, radius, nsample, mlp, mlp2, group_all, is_training, bn_decay, scope, bn=True, pooling='max', knn=False, use_xyz=True, use_nchw=False):\n    ''' PointNet Set Abstraction (SA) Module\n        Input:\n            xyz: (batch_size, ndataset, 3) TF tensor\n            points: (batch_size, ndataset, channel) TF tensor\n            npoint: int32 -- #points sampled in farthest point sampling\n            radius: float32 -- search radius in local region\n            nsample: int32 -- how many points in each local region\n            mlp: list of int32 -- output size for MLP on each point\n            mlp2: list of int32 -- output size for MLP on each region\n            group_all: bool -- group all points into one PC if set true, OVERRIDE\n                npoint, radius and nsample settings\n            use_xyz: bool, if True concat XYZ with local point features, otherwise just use point features\n            use_nchw: bool, if True, use NCHW data format for conv2d, which is usually faster than NHWC format\n        Return:\n            new_xyz: (batch_size, npoint, 3) TF tensor\n            new_points: (batch_size, npoint, mlp&#091;-1] or mlp2&#091;-1]) TF tensor\n            idx: (batch_size, npoint, nsample) int32 -- indices for local regions\n    '''\n    data_format = 'NCHW' if use_nchw else 'NHWC'\n    with tf.variable_scope(scope) as sc:\n        <em># Sample and Grouping<\/em>\n        if group_all:\n            nsample = xyz.get_shape()&#091;1].value\n            new_xyz, new_points, idx, grouped_xyz = sample_and_group_all(xyz, points, use_xyz)\n        else:\n            new_xyz, new_points, idx, grouped_xyz = sample_and_group(npoint, radius, nsample, xyz, points, knn, use_xyz)\n        <em># Point Feature Embedding<\/em>\n        if use_nchw: new_points = tf.transpose(new_points, &#091;0,3,1,2])\n        for i, num_out_channel in enumerate(mlp):\n            new_points = tf_util.conv2d(new_points, num_out_channel, &#091;1,1],\n                                        padding='VALID', stride=&#091;1,1],\n                                        bn=bn, is_training=is_training,\n                                        scope='conv%d'%(i), bn_decay=bn_decay,\n                                        data_format=data_format) \n        if use_nchw: new_points = tf.transpose(new_points, &#091;0,2,3,1])\n        <em># Pooling in Local Regions<\/em>\n        if pooling=='max':\n            new_points = tf.reduce_max(new_points, axis=&#091;2], keep_dims=True, name='maxpool')\n        elif pooling=='avg':\n            new_points = tf.reduce_mean(new_points, axis=&#091;2], keep_dims=True, name='avgpool')\n        elif pooling=='weighted_avg':\n            with tf.variable_scope('weighted_avg'):\n                dists = tf.norm(grouped_xyz,axis=-1,ord=2,keep_dims=True)\n                exp_dists = tf.exp(-dists * 5)\n                weights = exp_dists\/tf.reduce_sum(exp_dists,axis=2,keep_dims=True) <em># (batch_size, npoint, nsample, 1)<\/em>\n                new_points *= weights <em># (batch_size, npoint, nsample, mlp&#091;-1])<\/em>\n                new_points = tf.reduce_sum(new_points, axis=2, keep_dims=True)\n        elif pooling=='max_and_avg':\n            max_points = tf.reduce_max(new_points, axis=&#091;2], keep_dims=True, name='maxpool')\n            avg_points = tf.reduce_mean(new_points, axis=&#091;2], keep_dims=True, name='avgpool')\n            new_points = tf.concat(&#091;avg_points, max_points], axis=-1)\n        <em># &#091;Optional] Further Processing <\/em>\n        if mlp2 is not None:\n            if use_nchw: new_points = tf.transpose(new_points, &#091;0,3,1,2])\n            for i, num_out_channel in enumerate(mlp2):\n                new_points = tf_util.conv2d(new_points, num_out_channel, &#091;1,1],\n                                            padding='VALID', stride=&#091;1,1],\n                                            bn=bn, is_training=is_training,\n                                            scope='conv_post_%d'%(i), bn_decay=bn_decay,\n                                            data_format=data_format) \n            if use_nchw: new_points = tf.transpose(new_points, &#091;0,2,3,1])\n        new_points = tf.squeeze(new_points, &#091;2]) <em># (batch_size, npoints, mlp2&#091;-1])<\/em>\n        return new_xyz, new_points, idx<\/code><\/pre>\n\n\n\n<h4>2.1.1 sampling layer<\/h4>\n\n\n\n<p>       \u4f7f\u7528FPS\uff08\u6700\u8fdc\u70b9\u91c7\u6837\uff09\u5bf9\u70b9\u96c6\u8fdb\u884c\u964d\u91c7\u6837\uff0c\u5c06\u8f93\u5165\u70b9\u96c6\u4ece\u89c4\u6a21&nbsp;N1&nbsp;\u964d\u5230\u66f4\u5c0f\u7684\u89c4\u6a21&nbsp;N2&nbsp;\u3002FPS\u53ef\u4ee5\u7406\u89e3\u6210\u662f\u4f7f\u5f97\u91c7\u6837\u7684\u5404\u4e2a\u70b9\u4e4b\u95f4\u5c3d\u53ef\u80fd\u8fdc\uff0c\u8fd9\u79cd\u91c7\u6837\u7684\u597d\u5904\u662f\u53ef\u4ee5\u964d\u91c7\u6837\u7ed3\u679c\u4f1a\u6bd4\u8f83\u5747\u5300\u3002<\/p>\n\n\n\n<p><strong>FPS\u5b9e\u73b0\u65b9\u5f0f\u5982\u4e0b<\/strong>\uff1a\u968f\u673a\u9009\u62e9\u4e00\u4e2a\u70b9\u4f5c\u4e3a\u521d\u59cb\u70b9\u4f5c\u4e3a\u5df2\u9009\u62e9\u91c7\u6837\u70b9\uff0c\u8ba1\u7b97\u672a\u9009\u62e9\u91c7\u6837\u70b9\u96c6\u4e2d\u6bcf\u4e2a\u70b9\u4e0e\u5df2\u9009\u62e9\u91c7\u6837\u70b9\u96c6\u4e4b\u95f4\u7684\u8ddd\u79bbdistance\uff0c\u5c06\u8ddd\u79bb\u6700\u5927\u7684\u90a3\u4e2a\u70b9\u52a0\u5165\u5df2\u9009\u62e9\u91c7\u6837\u70b9\u96c6\uff0c\u7136\u540e\u66f4\u65b0distance\uff0c\u4e00\u76f4\u5faa\u73af\u8fed\u4ee3\u4e0b\u53bb\uff0c\u76f4\u81f3\u83b7\u5f97\u4e86\u76ee\u6807\u6570\u91cf\u7684\u91c7\u6837\u70b9\u3002<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>class FarthestSampler:\n    def __init__(self):\n        pass\n    def _calc_distances(self, p0, points):\n        return ((p0 - points) ** 2).sum(axis=1)\n    def __call__(self, pts, k):\n        farthest_pts = np.zeros((k, 3), dtype=np.float32)\n        farthest_pts&#091;0] = pts&#091;np.random.randint(len(pts))]\n        distances = self._calc_distances(farthest_pts&#091;0], pts)\n        for i in range(1, k):\n            farthest_pts&#091;i] = pts&#091;np.argmax(distances)]\n            distances = np.minimum(\n                distances, self._calc_distances(farthest_pts&#091;i], pts))\n        return farthest_pts<\/code><\/pre>\n\n\n\n<p>\u8f93\u5165\u89c4\u6a21\u4e3a&nbsp;B\u2217N\u2217(d+C)&nbsp;\uff0c\u5176\u4e2d&nbsp;B&nbsp;\u8868\u793abatch size\uff0c&nbsp;N&nbsp;\u8868\u793a\u70b9\u96c6\u4e2d\u70b9\u7684\u6570\u91cf\uff0c&nbsp;d&nbsp;\u8868\u793a\u70b9\u7684\u5750\u6807\u7ef4\u5ea6\uff0c&nbsp;C&nbsp;\u8868\u793a\u70b9\u7684\u5176\u4ed6\u7279\u5f81\uff08\u6bd4\u5982\u6cd5\u5411\u91cf\u7b49\uff09\u7ef4\u5ea6\u3002\u4e00\u822c&nbsp;d=3&nbsp;\uff0c&nbsp;c=0<\/p>\n\n\n\n<p>\u8f93\u51fa\u89c4\u6a21\u4e3a&nbsp;B\u2217N1\u2217(d+C)&nbsp;\uff0c&nbsp;N1&lt;N&nbsp;\uff0c\u56e0\u4e3a\u8fd9\u662f\u4e00\u4e2a\u964d\u91c7\u6837\u8fc7\u7a0b\u3002<\/p>\n\n\n\n<p><strong>sampling\u548cgrouping\u5177\u4f53\u5b9e\u73b0\u662f\u5199\u5728\u4e00\u4e2a\u51fd\u6570\u91cc\u7684\uff1a<\/strong><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>def sample_and_group(npoint, radius, nsample, xyz, points, knn=False, use_xyz=True):\n    '''\n    Input:\n        npoint: int32\n        radius: float32\n        nsample: int32\n        xyz: (batch_size, ndataset, 3) TF tensor\n        points: (batch_size, ndataset, channel) TF tensor, if None will just use xyz as points\n        knn: bool, if True use kNN instead of radius search\n        use_xyz: bool, if True concat XYZ with local point features, otherwise just use point features\n    Output:\n        new_xyz: (batch_size, npoint, 3) TF tensor\n        new_points: (batch_size, npoint, nsample, 3+channel) TF tensor\n        idx: (batch_size, npoint, nsample) TF tensor, indices of local points as in ndataset points\n        grouped_xyz: (batch_size, npoint, nsample, 3) TF tensor, normalized point XYZs\n            (subtracted by seed point XYZ) in local regions\n    '''\n    new_xyz = gather_point(xyz, farthest_point_sample(npoint, xyz)) <em># (batch_size, npoint, 3)<\/em>\n    if knn:\n        _,idx = knn_point(nsample, xyz, new_xyz)\n    else:\n        idx, pts_cnt = query_ball_point(radius, nsample, xyz, new_xyz)\n    grouped_xyz = group_point(xyz, idx) <em># (batch_size, npoint, nsample, 3)<\/em>\n    grouped_xyz -= tf.tile(tf.expand_dims(new_xyz, 2), &#091;1,1,nsample,1]) <em># translation normalization<\/em>\n    if points is not None:\n        grouped_points = group_point(points, idx) <em># (batch_size, npoint, nsample, channel)<\/em>\n        if use_xyz:\n            new_points = tf.concat(&#091;grouped_xyz, grouped_points], axis=-1) <em># (batch_size, npoint, nample, 3+channel)<\/em>\n        else:\n            new_points = grouped_points\n    else:\n        new_points = grouped_xyz\n    return new_xyz, new_points, idx, grouped_xyz<\/code><\/pre>\n\n\n\n<p>\u5176\u4e2dsampling\u5bf9\u5e94\u7684\u90e8\u5206\u662f\uff1a<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>new_xyz = gather_point(xyz, farthest_point_sample(npoint, xyz)) <em># (batch_size, npoint, 3)<\/em><\/code><\/pre>\n\n\n\n<p>      xyz\u65e2\u662f&nbsp;B\u2217N\u22173&nbsp;\u7684\u70b9\u4e91\uff0cnpoint\u662f\u964d\u91c7\u6837\u70b9\u7684\u89c4\u6a21\u3002\u6ce8\u610f\uff1aPointNet++\u7684FPS\u5747\u662f\u5728\u5750\u6807\u7a7a\u95f4\u505a\u7684\uff0c\u800c\u4e0d\u662f\u5728\u7279\u5f81\u7a7a\u95f4\u505a\u7684\u3002\u8fd9\u4e00\u70b9\u5f88\u5173\u952e\uff0c\u56e0\u4e3aFPS\u672c\u8eab\u662f\u4e0d\u53ef\u5fae\u7684\uff0c\u65e0\u6cd5\u8ba1\u7b97\u68af\u5ea6\u53cd\u5411\u4f20\u64ad\u3002<\/p>\n\n\n\n<p>\u672c\u7740\u5228\u6839\u95ee\u9898\u7684\u5fc3\u6001\uff0c\u6211\u4eec\u6765\u770b\u770bfarthest_point_sample\u548cgather_point\u7a76\u7adf\u5728\u505a\u4ec0\u4e48<\/p>\n\n\n\n<p>farthest_point_sample\u8f93\u5165\u8f93\u51fa\u975e\u5e38\u660e\u6670\uff0c\u8f93\u51fa\u7684\u662f\u964d\u91c7\u6837\u70b9\u5728inp\u4e2d\u7684\u7d22\u5f15\uff0c\u56e0\u6b64\u662f&nbsp;B\u2217N1&nbsp;int32\u7c7b\u578b\u7684\u5f20\u91cf<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>def farthest_point_sample(npoint,inp):\n    '''\ninput:\n    int32\n    batch_size * ndataset * 3   float32\nreturns:\n    batch_size * npoint         int32\n    '''\n    return sampling_module.farthest_point_sample(inp, npoint)<\/code><\/pre>\n\n\n\n<p>gather_point\u7684\u4f5c\u7528\u5c31\u662f\u5c06\u4e0a\u9762\u8f93\u51fa\u7684\u7d22\u5f15\uff0c\u8f6c\u5316\u6210\u771f\u6b63\u7684\u70b9\u4e91<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>def gather_point(inp,idx):\n    '''\ninput:\n    batch_size * ndataset * 3   float32\n    batch_size * npoints        int32\nreturns:\n    batch_size * npoints * 3    float32\n    '''\n    return sampling_module.gather_point(inp,idx)<\/code><\/pre>\n\n\n\n<h4><strong>2.1.2 grouping layer<\/strong><\/h4>\n\n\n\n<p>        \u4e0a\u4e00\u6b65sampling\u7684\u8fc7\u7a0b\u662f\u5c06&nbsp;N\u2217(d+C)&nbsp;\u964d\u5230&nbsp;N1\u2217(d+C)&nbsp;\uff08\u8fd9\u91cc\u8bba\u8ff0\u65b9\u4fbf\u5148\u4e0d\u8003\u8651batch\uff0c\u5c31\u8003\u8651\u5355\u4e2a\u70b9\u4e91\uff09\uff0c\u5b9e\u9645\u4e0a\u53ef\u4ee5\u7406\u89e3\u6210\u662f\u5728&nbsp;N&nbsp;\u4e2a\u70b9\u4e2d\u9009\u53d6&nbsp;N1&nbsp;\u4e2a\u4e2d\u5fc3\u70b9(key point)\u3002<\/p>\n\n\n\n<p>        \u90a3\u4e48\u8fd9\u4e00\u6b65grouping\u7684\u76ee\u7684\u5c31\u662f\u4ee5\u8fd9\u6bcf\u4e2akey point\u4e3a\u4e2d\u5fc3\uff0c\u627e\u5176\u56fa\u5b9a\u89c4\u6a21\uff08\u4ee4\u89c4\u6a21\u4e3a&nbsp;K\uff09\u7684\u90bb\u70b9\uff0c\u5171\u540c\u7ec4\u6210\u4e00\u4e2a\u5c40\u90e8\u90bb\u57df(patch)\u3002\u4e5f\u5c31\u662f\u4f1a\u751f\u6210&nbsp;N1&nbsp;\u4e2a\u5c40\u90e8\u90bb\u57df\uff0c\u8f93\u51fa\u89c4\u6a21\u4e3a&nbsp;N1\u2217K\u2217(d+C)<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>if knn:\n    _,idx = knn_point(nsample, xyz, new_xyz)\nelse:\n    idx, pts_cnt = query_ball_point(radius, nsample, xyz, new_xyz)\n    grouped_xyz = group_point(xyz, idx) <em># (batch_size, npoint, nsample, 3)<\/em><\/code><\/pre>\n\n\n\n<p>1)<strong>\u627e\u90bb\u57df\u7684\u8fc7\u7a0b\u4e5f\u662f\u5728\u5750\u6807\u7a7a\u95f4\u8fdb\u884c\uff08\u4e5f\u5c31\u662f\u4ee5\u4e0a\u4ee3\u7801\u8f93\u5165\u8f93\u51fa\u7ef4\u5ea6\u90fd\u662f<\/strong>&nbsp;d&nbsp;<strong>\uff0c\u6ca1\u6709<\/strong>&nbsp;C&nbsp;<strong>\uff0c<\/strong>&nbsp;C&nbsp;<strong>\u662f\u5728\u540e\u9762\u7684\u4ee3\u7801\u62fc\u63a5\u4e0a\u7684\uff09\uff0c\u800c\u4e0d\u662f\u7279\u5f81\u7a7a\u95f4\u3002<\/strong><\/p>\n\n\n\n<p>2)\u627e\u90bb\u57df\u8fd9\u91cc\u6709\u4e24\u79cd\u65b9\u5f0f\uff1aKNN\u548cquery ball point.<\/p>\n\n\n\n<p>\u5176\u4e2d\u524d\u8005KNN\u5c31\u662f\u5927\u5bb6\u8033\u719f\u80fd\u8be6\u7684K\u8fd1\u90bb\uff0c\u627eK\u4e2a\u5750\u6807\u7a7a\u95f4\u6700\u8fd1\u7684\u70b9\u3002<br>\u540e\u8005query ball point\u5c31\u662f\u5212\u5b9a\u67d0\u4e00\u534a\u5f84\uff0c\u627e\u5728\u8be5\u534a\u5f84\u7403\u5185\u7684\u70b9\u4f5c\u4e3a\u90bb\u70b9\u3002<\/p>\n\n\n\n<p>\u8fd8\u6709\u4e2a\u95ee\u9898\uff1aquery ball point\u5982\u4f55\u4fdd\u8bc1\u5bf9\u4e8e\u6bcf\u4e2a\u5c40\u90e8\u90bb\u57df\uff0c\u91c7\u6837\u70b9\u7684\u6570\u91cf\u90fd\u662f\u4e00\u6837\u7684\u5462\uff1f<br>\u4e8b\u5b9e\u4e0a\uff0c\u5982\u679cquery ball\u7684\u70b9\u6570\u91cf\u5927\u4e8e\u89c4\u6a21&nbsp;K&nbsp;\uff0c\u90a3\u4e48\u76f4\u63a5\u53d6\u524d&nbsp;K&nbsp;\u4e2a\u4f5c\u4e3a\u5c40\u90e8\u90bb\u57df\uff1b\u5982\u679c\u5c0f\u4e8e\uff0c\u90a3\u4e48\u76f4\u63a5\u5bf9\u67d0\u4e2a\u70b9\u91cd\u91c7\u6837\uff0c\u51d1\u591f\u89c4\u6a21&nbsp;K<\/p>\n\n\n\n<p>KNN\u548cquery ball\u7684\u533a\u522b\uff1a\uff08\u6458\u81ea\u539f\u6587\uff09Compared with kNN, ball query&#8217;s local neighborhood guarantees a fixed region scale thus making local region feature more generalizable across space, which is preferred for tasks requiring local pattern recognition (e.g. semantic point labeling).\u4e5f\u5c31\u662fquery ball\u66f4\u52a0\u9002\u5408\u4e8e\u5e94\u7528\u5728\u5c40\u90e8\/\u7ec6\u8282\u8bc6\u522b\u7684\u5e94\u7528\u4e0a\uff0c\u6bd4\u5982\u5c40\u90e8\u5206\u5272\u3002<\/p>\n\n\n\n<p>\u8865\u5145\u6750\u6599\u4e2d\u4e5f\u6709\u5b9e\u9a8c\u6765\u5bf9\u6bd4KNN\u548cquery ball:<\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" width=\"1024\" height=\"149\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-71-1024x149.png\" alt=\"\" class=\"wp-image-9389\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-71-1024x149.png 1024w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-71-300x44.png 300w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-71-768x112.png 768w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-71.png 1053w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><\/figure>\n\n\n\n<p>sample_and_group\u4ee3\u7801\u7684\u5269\u4f59\u90e8\u5206\uff1a<\/p>\n\n\n\n<p>sample\u548cgroup\u64cd\u4f5c\u90fd\u662f\u5728\u5750\u6807\u7a7a\u95f4\u8fdb\u884c\u7684\uff0c\u56e0\u6b64\u5982\u679c\u8fd8\u6709\u7279\u5f81\u7a7a\u95f4\u4fe1\u606f\uff08\u5373point-wise feature\uff09\uff0c\u53ef\u4ee5\u5728\u8fd9\u91cc\u5c06\u5176\u4e0e\u5750\u6807\u7a7a\u95f4\u62fc\u63a5\uff0c\u7ec4\u6210\u65b0\u7684point-wise feature\uff0c\u51c6\u5907\u9001\u5165\u540e\u9762\u7684unit point\u8fdb\u884c\u7279\u5f81\u5b66\u4e60\u3002<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>if points is not None:\n    grouped_points = group_point(points, idx) <em># (batch_size, npoint, nsample, channel)<\/em>\n    if use_xyz:\n        new_points = tf.concat(&#091;grouped_xyz, grouped_points], axis=-1) <em># (batch_size, npoint, nample, 3+channel)<\/em>\n    else:\n        new_points = grouped_points\nelse:\n    new_points = grouped_xyz<\/code><\/pre>\n\n\n\n<h4><strong>2.1.3 PointNet layer<\/strong><\/h4>\n\n\n\n<p>\u4f7f\u7528PointNet\u5bf9\u4ee5\u4e0a\u7ed3\u679c\u8868\u5f81<\/p>\n\n\n\n<p>\u8f93\u5165&nbsp;B\u2217N\u2217K\u2217(d+C)&nbsp;\uff0c\u8f93\u51fa&nbsp;B\u2217N\u2217(d+C1)<\/p>\n\n\n\n<p>\u4ee5\u4e0b\u4ee3\u7801\u4e3b\u8981\u5206\u62103\u4e2a\u90e8\u5206\uff1a<\/p>\n\n\n\n<p>1)point feature embedding<\/p>\n\n\n\n<p>\u8fd9\u91cc\u8f93\u5165\u662f&nbsp;B\u2217N\u2217K\u2217(d+C)&nbsp;\uff0c\u53ef\u4ee5\u7c7b\u6bd4\u6210\u662fbatch size\u4e3a&nbsp;B&nbsp;\uff0c\u5bbd\u9ad8\u4e3a&nbsp;N\u2217K&nbsp;\uff0c\u901a\u9053\u6570\u4e3a&nbsp;d+C&nbsp;\u7684\u56fe\u50cf\uff0c\u8fd9\u6837\u4e00\u7c7b\u6bd4\uff0c\u8fd9\u91cc\u7684\u5377\u79ef\u5c31\u597d\u7406\u89e3\u591a\u4e86\u5b9e\u9645\u4e0a\u5c31\u662f&nbsp;1\u22171&nbsp;\u5377\u79ef\uff0c\u4e0d\u6539\u53d8feature map\u5927\u5c0f\uff0c\u53ea\u6539\u53d8\u901a\u9053\u6570\uff0c\u5c06\u901a\u9053\u6570\u5347\u9ad8\uff0c\u5b9e\u73b0\u6240\u8c13\u201cembedding\u201d<\/p>\n\n\n\n<p>\u8fd9\u90e8\u5206\u8f93\u51fa\u662f&nbsp;B\u2217N\u2217K\u2217C1<\/p>\n\n\n\n<p>2)pooling in local regions<\/p>\n\n\n\n<p>pooling\uff0c\u53ea\u662f\u662f\u5bf9\u6bcf\u4e2a\u5c40\u90e8\u90bb\u57dfpooling,\u8f93\u51fa\u662f&nbsp;B\u2217N\u22171\u2217C1<\/p>\n\n\n\n<p>3)further processing<\/p>\n\n\n\n<p>     \u518d\u5bf9\u6c60\u5316\u540e\u7684\u7ed3\u679c\u505aMLP\uff0c\u4e5f\u662f\u7b80\u5355\u7684&nbsp;1\u22171&nbsp;\u5377\u79ef\u3002\u8fd9\u4e00\u90e8\u5206\u5728\u5b9e\u9645\u5b9e\u9a8c\u4e2dPointNet++\u5e76\u6ca1\u6709\u8bbe\u7f6e\u53bb\u505a<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code><em># Point Feature Embedding<\/em>\nif use_nchw: new_points = tf.transpose(new_points, &#091;0,3,1,2])\nfor i, num_out_channel in enumerate(mlp):\n    new_points = tf_util.conv2d(new_points, num_out_channel, &#091;1,1],\n                                padding='VALID', stride=&#091;1,1],\n                                bn=bn, is_training=is_training,\n                                scope='conv%d'%(i), bn_decay=bn_decay,\n                                data_format=data_format) \nif use_nchw: new_points = tf.transpose(new_points, &#091;0,2,3,1])\n\n<em># Pooling in Local Regions<\/em>\nif pooling=='max':\n    new_points = tf.reduce_max(new_points, axis=&#091;2], keep_dims=True, name='maxpool')\nelif pooling=='avg':\n    new_points = tf.reduce_mean(new_points, axis=&#091;2], keep_dims=True, name='avgpool')\nelif pooling=='weighted_avg':\n    with tf.variable_scope('weighted_avg'):\n        dists = tf.norm(grouped_xyz,axis=-1,ord=2,keep_dims=True)\n        exp_dists = tf.exp(-dists * 5)\n        weights = exp_dists\/tf.reduce_sum(exp_dists,axis=2,keep_dims=True) <em># (batch_size, npoint, nsample, 1)<\/em>\n        new_points *= weights <em># (batch_size, npoint, nsample, mlp&#091;-1])<\/em>\n        new_points = tf.reduce_sum(new_points, axis=2, keep_dims=True)\nelif pooling=='max_and_avg':\n    max_points = tf.reduce_max(new_points, axis=&#091;2], keep_dims=True, name='maxpool')\n    avg_points = tf.reduce_mean(new_points, axis=&#091;2], keep_dims=True, name='avgpool')\n    new_points = tf.concat(&#091;avg_points, max_points], axis=-1)\n\n<em># &#091;Optional] Further Processing <\/em>\nif mlp2 is not None:\n    if use_nchw: new_points = tf.transpose(new_points, &#091;0,3,1,2])\n    for i, num_out_channel in enumerate(mlp2):\n        new_points = tf_util.conv2d(new_points, num_out_channel, &#091;1,1],\n                                    padding='VALID', stride=&#091;1,1],\n                                    bn=bn, is_training=is_training,\n                                    scope='conv_post_%d'%(i), bn_decay=bn_decay,\n                                    data_format=data_format) \n    if use_nchw: new_points = tf.transpose(new_points, &#091;0,2,3,1])<\/code><\/pre>\n\n\n\n<h4><strong>2.1.4 Encoder\u8fd8\u6709\u4e00\u4e2a\u95ee\u9898<\/strong><\/h4>\n\n\n\n<p>pointnet++\u5b9e\u9645\u4e0a\u5c31\u662f\u5bf9\u5c40\u90e8\u90bb\u57df\u8868\u5f81\u3002<\/p>\n\n\n\n<p>       \u90a3\u5c31\u4e0d\u5f97\u4e0d\u9762\u5bf9\u4e00\u4e2a\u6311\u6218\uff1anon-uniform sampling density(\u70b9\u4e91\u7684\u5bc6\u5ea6\u4e0d\u5747\u5300)\uff0c\u4e5f\u5c31\u662f\u5728\u7a00\u758f\u70b9\u4e91\u5c40\u90e8\u90bb\u57df\u8bad\u7ec3\u53ef\u80fd\u4e0d\u80fd\u5f88\u597d\u6316\u6398\u70b9\u4e91\u7684\u5c40\u90e8\u7ed3\u6784<\/p>\n\n\n\n<p>PointNet++\u505a\u6cd5\uff1alearn to combine features from regions of different scales when the input sampling density changes.<\/p>\n\n\n\n<p>\u56e0\u6b64\u6587\u7ae0\u63d0\u51fa\u4e86\u4e24\u4e2a\u65b9\u6848\uff1a<\/p>\n\n\n\n<p>\u4e00\u3001Multi-scale grouping\uff08MSG\uff09<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter size-full\"><img loading=\"lazy\" width=\"231\" height=\"304\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-73.png\" alt=\"\" class=\"wp-image-9406\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-73.png 231w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-73-228x300.png 228w\" sizes=\"(max-width: 231px) 100vw, 231px\" \/><\/figure><\/div>\n\n\n\n<p>\u5bf9\u5f53\u524d\u5c42\u7684\u6bcf\u4e2a\u4e2d\u5fc3\u70b9\uff0c\u53d6\u4e0d\u540cradius\u7684query ball\uff0c\u53ef\u4ee5\u5f97\u5230\u591a\u4e2a\u4e0d\u540c\u5927\u5c0f\u7684\u540c\u5fc3\u7403\uff0c\u4e5f\u5c31\u662f\u5f97\u5230\u4e86\u591a\u4e2a\u76f8\u540c\u4e2d\u5fc3\u4f46\u89c4\u6a21\u4e0d\u540c\u7684\u5c40\u90e8\u90bb\u57df\uff0c\u5206\u522b\u5bf9\u8fd9\u4e9b\u5c40\u90e8\u90bb\u57df\u8868\u5f81\uff0c\u5e76\u5c06\u6240\u6709\u8868\u5f81\u62fc\u63a5\u3002\u5982\u4e0a\u56fe\u6240\u793a\u3002<\/p>\n\n\n\n<p>\u8be5\u65b9\u6cd5\u6bd4\u8f83\u9ebb\u70e6\uff0c\u8fd0\u7b97\u8f83\u591a\u3002<\/p>\n\n\n\n<p>\u4ee3\u7801\u5c42\u9762\u5176\u5b9e\u5c31\u662f\u52a0\u4e86\u4e2a\u904d\u5386radius_list\u7684\u5faa\u73af\uff0c\u5206\u522b\u5904\u7406\uff0c\u5e76\u6700\u540econcat<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>new_xyz = gather_point(xyz, farthest_point_sample(npoint, xyz))\nnew_points_list = &#091;]\nfor i in range(len(radius_list)):\n    radius = radius_list&#091;i]\n    nsample = nsample_list&#091;i]\n    idx, pts_cnt = query_ball_point(radius, nsample, xyz, new_xyz)\n    grouped_xyz = group_point(xyz, idx)\n    grouped_xyz -= tf.tile(tf.expand_dims(new_xyz, 2), &#091;1,1,nsample,1])\n    if points is not None:\n        grouped_points = group_point(points, idx)\n        if use_xyz:\n            grouped_points = tf.concat(&#091;grouped_points, grouped_xyz], axis=-1)\n    else:\n        grouped_points = grouped_xyz\n    if use_nchw: grouped_points = tf.transpose(grouped_points, &#091;0,3,1,2])\n    for j,num_out_channel in enumerate(mlp_list&#091;i]):\n        grouped_points = tf_util.conv2d(grouped_points, num_out_channel, &#091;1,1],\n                                        padding='VALID', stride=&#091;1,1], bn=bn, is_training=is_training,\n                                        scope='conv%d_%d'%(i,j), bn_decay=bn_decay)\n    if use_nchw: grouped_points = tf.transpose(grouped_points, &#091;0,2,3,1])\n    new_points = tf.reduce_max(grouped_points, axis=&#091;2])\n    new_points_list.append(new_points)\nnew_points_concat = tf.concat(new_points_list, axis=-1)<\/code><\/pre>\n\n\n\n<p>\u4e8c\u3001Multi-resolution grouping\uff08MRG\uff09<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter\"><img src=\"https:\/\/pic2.zhimg.com\/80\/v2-9027f24c6fe997d36934f676a43cb885_1440w.webp\" alt=\"\"\/><\/figure><\/div>\n\n\n\n<p>\uff08\u6458\u81ea\u539f\u6587\uff09features of a region at some level Li is a concatenation of two vectors.<\/p>\n\n\n\n<p>One vector (left in figure) is obtained by<strong>&nbsp;summarizing the features at each subregion from the lower level&nbsp;<\/strong>Li\u22121&nbsp;using the set abstraction level.<\/p>\n\n\n\n<p>The other vector (right) is the feature that is obtained by&nbsp;<strong>directly processing all raw points in the local region using a single PointNet<\/strong>.<\/p>\n\n\n\n<p>\u7b80\u5355\u6765\u8bf4\uff0c\u5c31\u662f\u5f53\u524dset abstraction\u7684\u5c40\u90e8\u90bb\u57df\u8868\u5f81\u7531\u4e24\u90e8\u5206\u6784\u6210\uff1a<\/p>\n\n\n\n<p>\u5de6\u8fb9\u8868\u5f81\uff1a\u5bf9\u4e0a\u4e00\u5c42set abstraction\uff08\u8fd8\u8bb0\u5f97\u4e0a\u4e00\u5c42\u7684\u70b9\u89c4\u6a21\u662f\u66f4\u5927\u7684\u5417\uff1f\uff09\u5404\u4e2a\u5c40\u90e8\u90bb\u57df\uff08\u6216\u8005\u8bf4\u4e2d\u5fc3\u70b9\uff09\u7684\u7279\u5f81\u8fdb\u884c\u805a\u5408\u3002  \u53f3\u8fb9\u8868\u5f81\uff1a\u4f7f\u7528\u4e00\u4e2a\u5355\u4e00\u7684PointNet\u76f4\u63a5\u5728\u5c40\u90e8\u90bb\u57df\u5904\u7406\u539f\u59cb\u70b9\u4e91<\/p>\n\n\n\n<h3><strong>2.2 decoder\uff1a<\/strong><\/h3>\n\n\n\n<h4><strong>2.2.1 \u5206\u7c7b\u4efb\u52a1\u7684decoder<\/strong><\/h4>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter size-full is-resized\"><img loading=\"lazy\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-74.png\" alt=\"\" class=\"wp-image-9414\" width=\"508\" height=\"177\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-74.png 672w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-74-300x104.png 300w\" sizes=\"(max-width: 508px) 100vw, 508px\" \/><\/figure><\/div>\n\n\n\n<p>\u6bd4\u8f83\u7b80\u5355\uff0c\u5c06encoder\u964d\u91c7\u6837\u5f97\u5230\u7684global feature\u9001\u5165\u51e0\u5c42\u5168\u8fde\u63a5\u7f51\u7edc\uff0c\u6700\u540e\u901a\u8fc7\u4e00\u4e2asoftmax\u5206\u7c7b\u3002<\/p>\n\n\n\n<h4><strong>2.2.2 \u5206\u5272\u4efb\u52a1\u7684decoder<\/strong><\/h4>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" width=\"1024\" height=\"418\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-75-1024x418.png\" alt=\"\" class=\"wp-image-9416\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-75-1024x418.png 1024w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-75-300x122.png 300w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-75-768x313.png 768w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-75.png 1382w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><\/figure>\n\n\n\n<p>\u7ecf\u8fc7\u524d\u534a\u90e8\u5206\u7684encoder\uff0c\u6211\u4eec\u5f97\u5230\u7684\u662fglobal feature\uff0c\u6216\u8005\u662f\u6781\u5c11\u6570\u70b9\u7684\u8868\u5f81\uff08\u5176\u5b9e\u4e5f\u5c31\u662fglobal feature\uff09<\/p>\n\n\n\n<p>\u800c\u5982\u679c\u505a\u5206\u5272\uff0c\u6211\u4eec\u9700\u8981\u7684\u662fpoint-wise feature\uff0c\u8fd9\u53ef\u600e\u4e48\u529e\u5462\uff1f<\/p>\n\n\n\n<p>PointNet\u5904\u7406\u601d\u8def\u5f88\u7b80\u5355\uff0c\u76f4\u63a5\u628aglobal feature\u590d\u5236\u5e76\u4e0e\u4e4b\u524d\u7684local feature\u62fc\u63a5\uff0c\u4f7f\u5f97\u8fd9\u4e2a\u65b0point-wise feature\u80fd\u591f\u83b7\u5f97\u4e00\u5b9a\u7a0b\u5ea6\u7684\u201c\u90bb\u57df\u201d\u4fe1\u606f\u3002\u8fd9\u79cd\u7b80\u5355\u7c97\u66b4\u7684\u65b9\u6cd5\u663e\u7136\u5e76\u4e0d\u80fd\u5f97\u5230\u5f88discriminative\u7684\u8868\u5f81<\/p>\n\n\n\n<p>\u522b\u6025\uff0cPointNet++\u6765\u4e86\u3002<\/p>\n\n\n\n<p>PointNet++\u8bbe\u8ba1\u4e86\u4e00\u79cd\u53cd\u5411\u63d2\u503c\u7684\u65b9\u6cd5\u6765\u5b9e\u73b0\u4e0a\u91c7\u6837\u7684decoder\u7ed3\u6784\uff0c\u901a\u8fc7\u53cd\u5411\u63d2\u503c\u548cskip connection\u6765\u83b7\u5f97discriminative point-wise feature\uff1a<\/p>\n\n\n\n<figure class=\"wp-block-image size-full\"><img loading=\"lazy\" width=\"681\" height=\"263\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/tempsnip.png\" alt=\"\" class=\"wp-image-9417\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/tempsnip.png 681w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/tempsnip-300x116.png 300w\" sizes=\"(max-width: 681px) 100vw, 681px\" \/><\/figure>\n\n\n\n<p>\u8bbe\u7ea2\u8272\u77e9\u5f62\u70b9\u96c6&nbsp;P1&nbsp;:&nbsp;N1\u2217C&nbsp;\uff0c\u84dd\u8272\u77e9\u5f62\u70b9\u96c6&nbsp;P2&nbsp;:&nbsp;N2\u2217C2&nbsp;\uff0c\u56e0\u4e3adecoder\u662f\u4e0a\u91c7\u6837\u8fc7\u7a0b\uff0c\u56e0\u6b64&nbsp;N2&gt;N1<\/p>\n\n\n\n<p><strong>\u4e00\u3001\u53cd\u5411\u63d2\u503c<\/strong>\u5177\u4f53\u505a\u6cd5\uff1a<\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" width=\"1024\" height=\"132\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-76-1024x132.png\" alt=\"\" class=\"wp-image-9421\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-76-1024x132.png 1024w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-76-300x39.png 300w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-76-768x99.png 768w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-76.png 1095w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><\/figure>\n\n\n\n<p>\u5bf9\u4e8e&nbsp;P2&nbsp;\u4e2d\u7684\u6bcf\u4e2a\u70b9&nbsp;x&nbsp;\uff0c\u627e\u5728\u539f\u59cb\u70b9\u4e91\u5750\u6807\u7a7a\u95f4\u4e0b\uff0c&nbsp;P1&nbsp;\u4e2d\u4e0e\u5176\u6700\u63a5\u8fd1\u7684&nbsp;k&nbsp;\u4e2a\u70b9&nbsp;x1,\u2026,xk<\/p>\n\n\n\n<p>\u5f53\u524d\u6211\u4eec\u60f3\u901a\u8fc7\u53cd\u5411\u63d2\u503c\u7684\u65b9\u5f0f\u7528\u8f83\u5c11\u7684\u70b9\u628a\u66f4\u591a\u7684\u70b9\u7684\u7279\u5f81\u63d2\u51fa\u6765\uff0c\u5b9e\u73b0\u4e0a\u91c7\u6837<\/p>\n\n\n\n<p>\u6b64\u65f6&nbsp;x1,\u2026,xk&nbsp;\u7684\u7279\u5f81\u6211\u4eec\u662f\u77e5\u9053\u7684\uff0c\u6211\u4eec\u60f3\u5f97\u5230&nbsp;x&nbsp;\u7684\u7279\u5f81\u3002\u5982\u4e0a\u516c\u5f0f\uff0c\u5b9e\u9645\u4e0a\u5c31\u662f\u5c06&nbsp;x1,\u2026,xk&nbsp;\u7684\u7279\u5f81\u52a0\u6743\u6c42\u548c\uff0c\u5f97\u5230x\u7684\u7279\u5f81\u3002\u5176\u4e2d\u8fd9\u4e2a\u6743\u91cd\u662f\u4e0ex\u548c&nbsp;x1,\u2026,xk&nbsp;\u7684\u8ddd\u79bb\u6210\u53cd\u5411\u76f8\u5173\u7684\uff0c\u610f\u601d\u5c31\u662f\u8ddd\u79bb\u8d8a\u8fdc\u7684\u70b9\uff0c\u5bf9x\u7279\u5f81\u7684\u8d21\u732e\u7a0b\u5ea6\u8d8a\u5c0f\u3002P2&nbsp;\u4e2d\u5176\u4ed6\u70b9\u4ee5\u6b64\u7c7b\u63a8\uff0c\u4ece\u800c\u5b9e\u73b0\u4e86\u7279\u5f81\u7684\u4e0a\u91c7\u6837\u56de\u4f20<\/p>\n\n\n\n<p><strong>\u4e8c<\/strong>\u3001<strong>skip connection<\/strong>\u5177\u4f53\u505a\u6cd5\uff1a<\/p>\n\n\n\n<p>      \u56de\u4f20\u5f97\u5230\u7684point-wise feature\u662f\u4ecedecoder\u7684\u4e0a\u4e00\u5c42\u5f97\u5230\u7684\uff0c\u56e0\u6b64\u7b97\u662fglobal\u7ea7\u522b\u7684\u4fe1\u606f\uff0c\u8fd9\u5bf9\u4e8e\u60f3\u5f97\u5230discriminative\u8fd8\u662f\u4e0d\u591f\uff0c\u56e0\u4e3a\u6211\u4eec\u8fd8\u7f3a\u5c11local\u7ea7\u522b\u7684\u4fe1\u606f\uff01\uff01\uff01<\/p>\n\n\n\n<p>\u5982\u4e0a\u56fe\u5c31\u662f\u6211\u4eec\u53cd\u5411\u63d2\u503c\u53ea\u5f97\u5230\u4e86&nbsp;C2&nbsp;\uff0c\u4f46\u662f\u6211\u4eec\u8fd8\u9700\u8981\u63d0\u4f9blocal\u7ea7\u522b\u4fe1\u606f\u7684&nbsp;C1&nbsp;\u7279\u5f81\uff01\uff01\uff01<\/p>\n\n\n\n<p>\u8fd9\u65f6skip connection\u6765\u4e86\uff01\uff01\uff01<\/p>\n\n\n\n<p>skip connection\u5176\u5b9e\u5c31\u662f\u5c06\u4e4b\u524dencoder\u5bf9\u5e94\u5c42\u7684\u8868\u5f81\u76f4\u63a5\u62fc\u63a5\u4e86\u8fc7\u6765<\/p>\n\n\n\n<p>\u56e0\u4e3a\u4e0a\u56fe\u4e2dencoder\u84dd\u8272\u77e9\u5f62\u70b9\u96c6\u7684&nbsp;C1&nbsp;\u8868\u5f81\u662f\u6765\u81ea\u4e8e\u89c4\u6a21\u66f4\u5927\u7684\u7eff\u8272\u77e9\u5f62\u70b9\u96c6\u7684\u8868\u5f81\uff0c\u8fd9\u5728\u4e00\u5b9a\u7a0b\u5ea6\u4e0a\u5176\u5b9e\u662f\u5b9e\u73b0\u4e86local\u7ea7\u522b\u7684\u4fe1\u606f<\/p>\n\n\n\n<p>\u6211\u4eec\u901a\u8fc7\u53cd\u5411\u63d2\u503c\u548cskip connection\u5728decoder\u4e2d\u9010\u7ea7\u4e0a\u91c7\u6837\u5f97\u5230local + global point-wise feature\uff0c\u5f97\u5230\u4e86discriminative feature\uff0c\u5e94\u7528\u4e8e\u5206\u5272\u4efb\u52a1\u3002<\/p>\n\n\n\n<h3><strong>2.3 loss<\/strong><\/h3>\n\n\n\n<p>\u65e0\u8bba\u662f\u5206\u7c7b\u8fd8\u662f\u5206\u5272\u5e94\u7528\uff0c\u672c\u8d28\u4e0a\u90fd\u662f\u5206\u7c7b\u95ee\u9898\uff0c\u56e0\u6b64loss\u5c31\u662f\u5206\u7c7b\u4efb\u52a1\u4e2d\u5e38\u7528\u7684\u4ea4\u53c9\u71b5loss<\/p>\n\n\n\n<h3><strong>2.4 \u5176\u4ed6\u7684\u95ee\u9898<\/strong><\/h3>\n\n\n\n<p>Q\uff1aPointNet++\u68af\u5ea6\u662f\u5982\u4f55\u56de\u4f20\u7684\uff1f\uff1f\uff1f<\/p>\n\n\n\n<p>A\uff1aPointNet++ fps\u5b9e\u9645\u4e0a\u5e76\u6ca1\u6709\u53c2\u4e0e\u68af\u5ea6\u8ba1\u7b97\u548c\u53cd\u5411\u4f20\u64ad\u3002<\/p>\n\n\n\n<p>\u53ef\u4ee5\u7406\u89e3\u6210\u662fPointNet++\u5c06\u70b9\u4e91\u8fdb\u884c\u4e0d\u540c\u89c4\u6a21\u7684fps\u964d\u91c7\u6837\uff0c\u4e8b\u5148\u5c06\u8fd9\u4e9b\u6570\u636e\u51c6\u5907\u597d\uff0c\u518d\u9001\u5230\u7f51\u7edc\u4e2d\u53bb\u8bad\u7ec3\u7684<\/p>\n\n\n\n<h2><strong>3 dataset and experiments<\/strong><\/h2>\n\n\n\n<h3><strong>3.1 dataset<\/strong><\/h3>\n\n\n\n<ul><li>MNIST: Images of handwritten digits with 60k training and 10k testing samples.\uff08\u7528\u4e8e\u5206\u7c7b\uff09<\/li><li>ModelNet40: CAD models of 40 categories (mostly man-made). We use the official split with 9,843 shapes for training and 2,468 for testing. \uff08\u7528\u4e8e\u5206\u7c7b\uff09<\/li><li>SHREC15: 1200 shapes from 50 categories. Each category contains 24 shapes which are mostly organic ones with various poses such as horses, cats, etc. We use five fold cross validation to acquire classification accuracy on this dataset. \uff08\u7528\u4e8e\u5206\u7c7b\uff09<\/li><li>ScanNet: 1513 scanned and reconstructed indoor scenes. We follow the experiment setting in [5] and use 1201 scenes for training, 312 scenes for test. \uff08\u7528\u4e8e\u5206\u5272\uff09<\/li><\/ul>\n\n\n\n<h3><strong>3.2 experiments<\/strong><\/h3>\n\n\n\n<p>\u4e3b\u8981\u5173\u5fc3\u7684\u5b9e\u9a8c\u7ed3\u679c\u662f2\u4e2a\uff1a<\/p>\n\n\n\n<ol><li>ModelNet40\u5206\u7c7b\u7ed3\u679c<\/li><li>ShapeNet Part\u5206\u5272\u7ed3\u679c<\/li><\/ol>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" width=\"1024\" height=\"262\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-77-1024x262.png\" alt=\"\" class=\"wp-image-9434\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-77-1024x262.png 1024w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-77-300x77.png 300w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-77-768x197.png 768w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-77.png 1425w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><\/figure>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" width=\"1024\" height=\"196\" src=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-78-1024x196.png\" alt=\"\" class=\"wp-image-9435\" srcset=\"http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-78-1024x196.png 1024w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-78-300x57.png 300w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-78-768x147.png 768w, http:\/\/139.9.1.231\/wp-content\/uploads\/2022\/10\/image-78.png 1499w\" sizes=\"(max-width: 1024px) 100vw, 1024px\" \/><figcaption>PointNet++\u4e5f\u505a\u4e86ShapeNet part\u6570\u636e\u96c6\u4e0a\u7684part segmentation\uff1a<\/figcaption><\/figure>\n\n\n\n<h2>4\u3001 conclusion<\/h2>\n\n\n\n<p>PointNet++\u662fPointNet\u7684\u7eed\u4f5c\uff0c\u5728\u4e00\u5b9a\u7a0b\u5ea6\u4e0a\u5f25\u8865\u4e86PointNet\u7684\u4e00\u4e9b\u7f3a\u9677\uff0c\u8868\u5f81\u7f51\u7edc\u57fa\u672c\u548cPN\u7c7b\u4f3c\uff0c\u8fd8\u662fMLP\u3001&nbsp;1\u22171&nbsp;\u5377\u79ef\u3001pooling\u90a3\u4e00\u5957\uff0c\u6838\u5fc3\u521b\u65b0\u70b9\u5728\u4e8e\u8bbe\u8ba1\u4e86\u5c40\u90e8\u90bb\u57df\u7684\u91c7\u6837\u8868\u5f81\u65b9\u6cd5\u548c\u8fd9\u79cd\u591a\u5c42\u6b21\u7684encoder-decoder\u7ed3\u5408\u7684\u7f51\u7edc\u7ed3\u6784\u3002<\/p>\n\n\n\n<p>\u7b2c\u4e00\u6b21\u770b\u5230PointNet++\u7f51\u7edc\u7ed3\u6784\uff0c\u89c9\u5f97\u8bbe\u8ba1\u5f97\u975e\u5e38\u7cbe\u5999\uff0c\u7279\u522b\u662f\u8bbe\u8ba1\u4e86\u4e0a\u91c7\u6837\u548c\u4e0b\u91c7\u6837\u7684\u5177\u4f53\u5b9e\u73b0\u65b9\u6cd5\uff0c\u5e76\u4ee5\u6b64\u7528\u4e8e\u5206\u5272\u4efb\u52a1\u7684\u8868\u5f81\uff0c\u89c9\u5f97\u8bbe\u8ba1\u5f97\u592a\u6f02\u4eae\u4e86\u3002\u4f46\u5176\u5b9e\u65e0\u8bba\u662f\u5206\u7c7b\u8fd8\u662f\u5206\u5272\u4efb\u52a1\uff0c\u63d0\u5347\u5e45\u5ea6\u8f83PointNet\u4e5f\u5c31\u662f1-2\u4e2a\u70b9\u800c\u5df2\u3002<\/p>\n\n\n\n<p>PointNet++\uff0c\u7279\u522b\u662f\u5176\u524d\u534a\u90e8\u5206encoder\uff0c\u63d0\u4f9b\u4e86\u975e\u5e38\u597d\u7684\u8868\u5f81\u7f51\u7edc\uff0c\u540e\u9762\u5f88\u591a\u70b9\u4e91\u5904\u7406\u5e94\u7528\u7684\u8bba\u6587\u90fd\u4f1a\u4f7f\u7528\u5230PointNet++\u4f5c\u4e3a\u5b83\u4eec\u7684\u8868\u5f81\u5668\u3002<\/p>\n","protected":false},"excerpt":{"rendered":"<p>\u8bba\u6587\uff1ahttps:\/\/arxiv.org\/abs\/1706.02413\uff08NIPS 2017\uff09 code\uff1a ht &hellip; <a href=\"http:\/\/139.9.1.231\/index.php\/2022\/10\/21\/pointnetplus\/\" class=\"more-link\">\u7ee7\u7eed\u9605\u8bfb<span class=\"screen-reader-text\">PointNet++<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[4,31,9],"tags":[],"_links":{"self":[{"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/posts\/9337"}],"collection":[{"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/comments?post=9337"}],"version-history":[{"count":87,"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/posts\/9337\/revisions"}],"predecessor-version":[{"id":9439,"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/posts\/9337\/revisions\/9439"}],"wp:attachment":[{"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/media?parent=9337"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/categories?post=9337"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/139.9.1.231\/index.php\/wp-json\/wp\/v2\/tags?post=9337"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}