【问题标题】:Android reading and graphing data from text file using GraphViewAndroid 使用 GraphView 从文本文件中读取和绘制数据
【发布时间】:2015-01-08 23:35:27
【问题描述】:

在我的 android 应用程序中,我试图从包含我希望绘制的数据点的文本文件中读取数据。每个文件中的数据点数量预计在 24,000 到 150,000 之间。

目前,我已经实现了一个异步任务,它从压缩文本文件中读取数据并将其存储在本地向量中。任务完成后,将数据点添加到数据集中以便绘制图表。

异步任务的代码实现如下:

class ReadFileService extends AsyncTask<Void, String, Boolean> {

    @Override
    protected Boolean doInBackground(Void... args) {        
        Scanner strings = null;
        InputStream stream = null;
        ZipInputStream zipInput = null;
        try {
            System.out.println(externalStorageDirectory + Constants.APP_DIRECTORY + recordingName + Constants.ZIP_FILE_EXTENTION);
            File file = new File(externalStorageDirectory + Constants.APP_DIRECTORY, recordingName + Constants.ZIP_FILE_EXTENTION);
            ZipFile zipFile = new ZipFile(file);
            Enumeration<? extends ZipEntry> entries = zipFile.entries();

            while (entries.hasMoreElements()) {
                ZipEntry zipEntry = entries.nextElement();
                stream = zipFile.getInputStream(zipEntry);
                strings = new Scanner(stream);

                // Extract the value of sampling frequency from header
                System.out.println("Extracting value of sampling frequency.");
                String regexPattern = "\"ColumnLabels\"";
                strings.useDelimiter(regexPattern);
                String extracted = strings.next();
                Pattern pattern = Pattern.compile("\"SamplingFrequency\": \"(\\d+)\"");
                Matcher matcher = pattern.matcher(extracted);
                if (matcher.find()) {
                    samplingFrequency = Integer.parseInt(matcher.group(1));
                    System.out.println(samplingFrequency);
                }

                // Locate the end of the header and use tabs as the delimiter
                strings.findWithinHorizon(endOfHeader,0);           
                strings.useDelimiter("\t *");
                strings.next();
            }
        }
        catch (FileNotFoundException error) {
            System.out.println("@IOERROR: " + error);
            return false;
        }
        catch (IOException error) {
            System.out.println("@IOERROR: " + error);
            return false;
        }
        while (strings.hasNext())
        {
            // Get raw value of data point
            double dataPoint = Double.parseDouble(strings.next());
            // Convert data point into the proper scale
            dataSet.add(SensorDataConverter.scaleEMG(dataPoint));
            // Skip the index value if it exists and break from loop if it does not
            if (strings.hasNext())
                strings.next();
            else
                break;
        }
        System.out.println("Closing strings.");
        try {
            stream.close();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        strings.close();            
        return true;
    }

    protected void onProgressUpdate(String...progress) {
        //called when the background task makes any progress
    }

    protected void onPreExecute() {
        //called before doInBackground() is started
        super.onPreExecute();
        // Show Progress Bar Dialog before calling doInBackground method
        prgDialog.setTitle("Opening File");
        prgDialog.setMessage("Opening " + recordingName + "\nPlease wait...");
        prgDialog.show();
    }

    //called after doInBackground() has finished
    protected void onPostExecute(Boolean readFileSuccess) { 
        // If unable to read from file, print error and generate a random set of sample data
        if(!readFileSuccess) {
            Random randomGenerator = new Random();          
            System.out.println("@IOERROR: Unable to read from file. Creating random dataset");
            for(int i=0; i<100; i++)
            {
                dataSet.add(randomGenerator.nextDouble());
            }
        }
        // Create a set of graph data to use with GraphView
        exampleSeries1 = new GraphViewSeries(new GraphViewData[] {
        });
        for (int i=0; i<dataSet.size(); i++) {
            double pointX = i;
            double pointY = dataSet.get(i);
            exampleSeries1.appendData(new GraphViewData(pointX, pointY), true, dataSet.size());
        }
        // Plot the data points
        graphData();
        prgDialog.dismiss();
        prgDialog = null;
    }
}

这似乎在保存和加载大约 10,000 个数据点时有效,加载时间大约为 15 秒。但是,当数据点数量跃升至 20,000 个时,加载时间最多需要 45 秒。

我的主要问题是:是否有另一种更有效地处理所有这些数据的方法,以最大限度地减少加载数据所需的时间?例如,是否可以动态绘制数据图表点取决于视口范围?

任何帮助和建议将不胜感激。

【问题讨论】:

    标签: java android graphing android-graphview


    【解决方案1】:

    您必须对数据重新采样以获得更少量的数据点。通常在单个视口上绘制超过 100 个数据点是没有意义的。

    并使用手动视口和手动标签宽度/高度来提高性能

    【讨论】:

    • 我担心可能是这种情况......这样做似乎很不方便,因为它会限制用户手动滚动和缩放图形的灵活性。但是,我感谢您的意见 - 我目前正在尝试首先提高文件读取速度,但如果这没有帮助,我会尝试您的建议。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多