【问题标题】:How to convert OpenCV Mat input frame to Tensorflow tensor in Android Studio?如何在 Android Studio 中将 OpenCV Mat 输入帧转换为 Tensorflow 张量?
【发布时间】:2020-07-20 13:17:46
【问题描述】:

我一直在尝试在 android 上运行 Tensorflow 模型。解决方案是首先创建一个 tensorflow 模型(我使用了预训练的 Mobilenetv2 模型)。在我自己的数据集上对其进行训练后,我将其转换为 Android 支持的 .tflite 模型。由于我想进行实时视频分析,所以我也在使用为 Android SDK 构建的 OpenCV 库。

现在我目前陷入困境的部分是 - 如何转换 opencv JavaCameraView 接收到的输入帧并将其提供给 tflite 模型进行推理?我发现很少有将 Mat 数据类型转换为输入张量的解决方案,但似乎没有什么清楚的。有人可以帮我解决这个问题吗?

编辑:这是代码(需要以下 onCameraFrame 方法的帮助)

public class MainActivity extends AppCompatActivity implements CameraBridgeViewBase.CvCameraViewListener2 {`enter code here`

    CameraBridgeViewBase cameraBridgeViewBase;
    BaseLoaderCallback baseLoaderCallback;
  //  int counter = 0;
    Interpreter it;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);


        cameraBridgeViewBase = (JavaCameraView)findViewById(R.id.CameraView);
        cameraBridgeViewBase.setVisibility(SurfaceView.VISIBLE);
        cameraBridgeViewBase.setCvCameraViewListener(this);
        try{
            it=new Interpreter(loadModelFile(this));
        }
        catch(Exception e){
            Toast.makeText(this,"Tf model didn't load",Toast.LENGTH_LONG).show();
        }

        //System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
        baseLoaderCallback = new BaseLoaderCallback(this) {
            @Override
            public void onManagerConnected(int status) {
                super.onManagerConnected(status);

                switch(status){

                    case BaseLoaderCallback.SUCCESS:
                        cameraBridgeViewBase.enableView();
                        break;
                    default:
                        super.onManagerConnected(status);
                        break;
                }


            }

        };




    }
    private MappedByteBuffer loadModelFile(Activity activity) throws IOException {
        AssetFileDescriptor fileDescriptor = activity.getAssets().openFd("model.tflite");
        FileInputStream inputStream = new FileInputStream(fileDescriptor.getFileDescriptor());
        FileChannel fileChannel = inputStream.getChannel();
        long startOffset = fileDescriptor.getStartOffset();
        long declaredLength = fileDescriptor.getDeclaredLength();
        return fileChannel.map(FileChannel.MapMode.READ_ONLY, startOffset, declaredLength);
    }
    @Override
    public Mat onCameraFrame(CameraBridgeViewBase.CvCameraViewFrame inputFrame) {

       //how to convert inputFrame to Input Tensor???



        
    }


    @Override
    public void onCameraViewStarted(int width, int height) {

    }


    @Override
    public void onCameraViewStopped() {

    }


    @Override
    protected void onResume() {
        super.onResume();

        if (!OpenCVLoader.initDebug()){
            Toast.makeText(getApplicationContext(),"There's a problem, yo!", Toast.LENGTH_SHORT).show();
        }

        else
        {
            baseLoaderCallback.onManagerConnected(baseLoaderCallback.SUCCESS);
        }



    }

    @Override
    protected void onPause() {
        super.onPause();
        if(cameraBridgeViewBase!=null){

            cameraBridgeViewBase.disableView();
        }

    }


    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (cameraBridgeViewBase!=null){
            cameraBridgeViewBase.disableView();
        }
    }
}

【问题讨论】:

  • @funie200 我添加了代码。

标签: java python android tensorflow opencv


【解决方案1】:

我建议你将Mat转换成FloatBuffer如下:

Mat floatMat = new Mat();
mat.convertTo(floatMat, CV_32F);
FloatBuffer floatBuffer = floatMat.createBuffer();

请注意,createBuffer 方法位于导入 org.bytedeco.opencv.opencv_core.MatMat 类中,而不是导入 org.opencv.core

然后您可以从floatBuffer 变量创建张量:

Tensor.create(new long[]{1, image_height, image_width, 3}, floatBuffer)

这将创建一个张量,其中包含一批图像(如最左侧的数字 1 所示),图像的尺寸为 (image_height, image_width, 3),您应该知道并替换它。大多数图像处理和机器学习库使用第一个维度表示图像的高度或“行”,第二个维度表示宽度或“列”,第三个维度表示通道数(RGB = 3 个通道)。如果您有灰度图像,则将 3 替换为 1。

请检查您是否可以直接将此张量输入您的模型,或者您必须先执行一些预处理步骤,例如标准化。

【讨论】:

    猜你喜欢
    • 2021-09-17
    • 2023-03-18
    • 2021-04-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-11-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多