You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何让水果病害检测APP在非水果图片下显示“未检测到植物”提示?

解决方案

方案一:基于置信度阈值快速处理(无需重新训练模型)

当前模型的所有输出类别均为水果相关,当用户上传非水果图片时,所有类别的置信度都会处于较低水平。我们可以设置一个置信度阈值(比如70%),若最高置信度低于该阈值,则判定为未检测到植物。

修改后的代码如下:

private void classifyImage(Bitmap image) {
    try {
        FruitDisease model = FruitDisease.newInstance(getApplicationContext());

        TensorBuffer inputFeature = TensorBuffer.createFixedSize(new int[]{1, 224, 224, 3}, DataType.FLOAT32);
        ByteBuffer byteBuffer = ByteBuffer.allocateDirect(4 * imageSize * imageSize * 3);
        byteBuffer.order(ByteOrder.nativeOrder());

        int[] intValue = new int[imageSize * imageSize];
        image.getPixels(intValue, 0, image.getWidth(), 0, 0, image.getWidth(), image.getHeight());

        int pixel = 0;
        for (int i = 0; i < imageSize; i++) {
            for (int j = 0; j < imageSize; j++) {
                int val = intValue[pixel++];
                byteBuffer.putFloat(((val >> 16) & 0xFF) * (1.f / 255.f));
                byteBuffer.putFloat(((val >> 8) & 0xFF) * (1.f / 255.f));
                byteBuffer.putFloat((val & 0xFF) * (1.f / 255.f));
            }
        }
        inputFeature.loadBuffer(byteBuffer);

        FruitDisease.Outputs outputs = model.process(inputFeature);
        TensorBuffer outputFeature0 = outputs.getOutputFeature0AsTensorBuffer();

        float[] confidences = outputFeature0.getFloatArray();
        int maxPos = 0;
        float maxConfidence = 0;
        for (int i = 0; i < confidences.length; i++) {
            if (confidences[i] > maxConfidence) {
                maxConfidence = confidences[i];
                maxPos = i;
            }
        }

        String[] classes = {"Watermelon Healthy", "Watermelon Blossom End Rot", "Watermelon Anthracnose",
                "Mango Healthy", "Mango Bacterial Canker", "Mango Anthracnose",
                "Orange Scab", "Orange Healthy",
                "Orange Bacterial Citrus Canker", "Banana Healthy", "Banana Crown Rot",
                "Banana Anthracnose", "Apple Scab", "Apple Healthy", "Apple Black Rot Canker"};

        // 新增置信度判断逻辑
        float confidenceThreshold = 0.7f; // 可根据实际测试调整阈值
        if (maxConfidence < confidenceThreshold) {
            result.setText("未检测到植物");
            confidence.setVisibility(View.GONE); // 隐藏置信度详情
        } else {
            result.setText(classes[maxPos]);
            String s = "";
            for (int i = 0; i < classes.length; i++) {
                s += String.format("%s: %.1f%%\n", classes[i], confidences[i] * 100);
            }
            confidence.setText(s);
            confidence.setVisibility(View.VISIBLE);
        }

        model.close(); // 关闭模型释放资源,避免内存泄漏
    } catch (IOException e) {
        e.printStackTrace();
    }
}
  • 调整建议:阈值需要用非水果图片测试后灵活调整,比如若大部分非水果图片的最高置信度在50%以下,可将阈值设为0.6或0.7,减少误判概率。
  • 额外优化:新增model.close()释放模型资源,防止内存泄漏。

方案二:重新训练模型(更精准的长期方案)

如果阈值判断容易出现误判(比如部分非水果图片恰好匹配到某水果类别的较高置信度),建议重新训练模型,添加*“非植物”*类别,训练时加入大量非植物样本(如日常物品、动物、风景等)。

这种方式下模型会直接输出“非植物”分类结果,比阈值判断的可靠性更高。

训练注意事项:

  • 保证“非植物”类别的样本数量与其他水果类别相当,避免类别不平衡影响模型效果。
  • 训练完成后替换原有FruitDisease模型,仅需在代码的classes数组中新增对应的“非植物”类别即可。

内容的提问来源于stack exchange,提问作者Lousy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.08 15:05:13