实现GPU上简单的int比较操作符

发布时间:2023年12月20日

头文件的定义

//filter.h
#ifndef __FILTER_HEADER__
#define __FILTER_HEADER__

#include <sstream>
#include <string>
#include <vector>

namespace ruda {

  const int RUDA_ERR = -1;
  const int RUDA_OK = 0;

  enum CompOperator {
    EQ = 0, LESS, GREATER, LESS_EQ, GREATER_EQ,
  };

  inline std::string toStringCompOperator(CompOperator op) {
    switch (op) {
      case EQ: return "EQ";
      case LESS: return "LESS";
      case GREATER: return "GREATER";
      case LESS_EQ: return "LESS_EQ";
      case GREATER_EQ: return "GREATER_EQ";
      default: return "INVALID";
    }
  }

  struct IntComparator {
    CompOperator _op;
    int _pivot;

    std::string toString() const {
      std::stringstream ss;
      ss << "_op: " << toStringCompOperator(this->_op) << ", "
        << "_pivot: " << _pivot;
      return ss.str();
    }
  };

  int sstIntFilter(const std::vector<int>& values,
                   const IntComparator rawComp,
                   std::vector<bool>& results);
}
#endif
//filter.cu
#include "filter.h"

#include <stdio.h>
#include <iostream>
#include <vector>
#include <string>
#include <thrust/device_vector.h>
#include <thrust/host_vector.h>
#include <thrust/transform.h>
#include <thrust/functional.h>
#include <algorithm>

namespace ruda {

  struct CudaIntComparator {
    IntComparator _rawComp;

    CudaIntComparator(IntComparator rawComp) {
      this->_rawComp = rawComp;
    }

    __host__ __device__
    bool operator()(const int target) {
      switch (this->_rawComp._op) {
        case EQ:
          return target == this->_rawComp._pivot;
        case LESS:
          return target < this->_rawComp._pivot;
        case GREATER:
          return target > this->_rawComp._pivot;
        case LESS_EQ:
          return target <= this->_rawComp._pivot;
        case GREATER_EQ:
          return target >= this->_rawComp._pivot;
        default:
          return false;
      }
    }

    std::string toString() {
      return this->_rawComp.toString();
    }
  };

  int sstIntFilter(const std::vector<int>& values,
                   const IntComparator rawComp,
                   std::vector<bool>& results) {
    std::cout << "[RUDA][sstIntFilter] Start" << std::endl;
    results.resize(values.size());

    std::cout << "[sstIntFilter] Inputs" << std::endl;
    std::cout << "[sstIntFilter] Inputs - values" << std::endl;
    for (int i = 0; i < values.size(); ++i) {
      std::cout << values[i] << " ";
    }
    std::cout << std::endl;
    std::cout << "[sstIntFilter] Inputs - rawComp: " << rawComp.toString()
        << std::endl;

    thrust::device_vector<int> d_values(values);
    thrust::device_vector<int> d_results(values.size());

    CudaIntComparator cudaComp(rawComp);

    std::cout << "[sstIntFilter] Devices" << std::endl;
    std::cout << "[sstIntFilter] Devices - d_values" << std::endl; //非并行的搬移数据到device
    for (int i = 0; i < d_values.size(); ++i) {
      std::cout << d_values[i] << " ";
    }
    std::cout << std::endl;
    std::cout << "[sstIntFilter] cudaComp: " << cudaComp.toString() << std::endl;

    thrust::copy_if(d_values.begin(), d_values.end(), d_results.begin(),
                    cudaComp);  //条件复制,按照cudaComp复制符合条件的value到result
    cudaDeviceSynchronize();

    std::cout << "[sstIntFilter] Results" << std::endl;
    std::cout << "[sstIntFilter] Results - d_results" << std::endl;
    for (int i = 0; i < d_results.size(); ++i) {
      std::cout << d_results[i] << " ";
    }
    std::cout << std::endl;

    thrust::copy(d_results.begin(), d_results.end(), results.begin());
    std::cout << "[sstIntFilter] Results - results" << std::endl;
    for (int i = 0; i < results.size(); ++i) {
      std::cout << results[i] << " ";
    }
    std::cout << std::endl;

    return ruda::RUDA_OK;
  }
}


//实现GPU上简单的int比较操作符

#include <iostream>
#include <vector>

#include "filter.h"

int main() {
    std::cout << "[FILTER_TEST] Starts" << std::endl;
    ruda::IntComparator comp = {
        ruda::GREATER_EQ, 5,
        };

    std::vector<int> values{ 1, 2, 3, 4, 5, 6, 7, 8, 9 };
    std::vector<bool> results;

    std::cout << "[FILTER_TEST] Run SST Filter" << std::endl;
    ruda::sstIntFilter(values, comp, results);

    std::cout << "[FILTER_TEST] Results" << std::endl;
    for (int i = 0; i < results.size(); ++i) {
        std::cout << results[i] << " ";
    }
    std::cout << std::endl;
    return 0;
}

CMakeLists.txt

cmake_minimum_required(VERSION 3.10)

project(FilterProject)

set(CMAKE_BUILD_TYPE Debug)
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED True)

find_package(CUDA REQUIRED)

include_directories(${CUDA_INCLUDE_DIRS})

cuda_add_library(filter STATIC filter.cu)

add_executable(runnable_filter_test filter_test.cc)

target_link_libraries(runnable_filter_test filter ${CUDA_LIBRARIES})

输出
在这里插入图片描述

文章来源:https://blog.csdn.net/weixin_40579705/article/details/135096756
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。