在Android App中读取CSV文件 [英] Reading CSV File In Android App
问题描述
我正在开发一个概念验证应用程序,以便可以在我正在开发的更大的应用程序中实现该功能.我对Java和Android Dev有点陌生,但希望这个问题不会太简单或太复杂.
I'm working on a proof-of-concept app so that I can implement the feature in a larger app I'm making. I'm a bit new to Java and Android Dev but hopefully this shouldn't be too simple or complex of a question.
基本上,我正在尝试从CSV文件中读取字符串列表,并使其可用于在应用程序的主活动中显示该列表.
Basically, I'm trying to read in a list of strings from a CSV file and make it usable in displaying the list on the app's Main Activity.
我正在使用一个外部类来读取CSV文件.这是课程代码:
I'm using an external class for reading in CSV's. Here's the class code:
CSVFile.java
package com.yourtechwhiz.listdisplay;
import android.util.Log;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.List;
public class CSVFile {
InputStream inputStream;
public CSVFile(InputStream inputStream){
this.inputStream = inputStream;
}
public List read(){
List resultList = new ArrayList();
BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream));
try {
String csvLine;
while ((csvLine = reader.readLine()) != null) {
String[] row = csvLine.split(",");
resultList.add(row);
Log.d("VariableTag", row[0].toString());
}
}
catch (IOException ex) {
throw new RuntimeException("Error in reading CSV file: "+ex);
}
finally {
try {
inputStream.close();
}
catch (IOException e) {
throw new RuntimeException("Error while closing input stream: "+e);
}
}
return resultList;
}
}
这是我的主要活动代码:
Here's my main activity code:
MainActivity.java
package com.yourtechwhiz.listdisplay;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.List;
public class MainActivity extends AppCompatActivity {
// Array of strings that's used to display on screen
String[] mobileArray = {"Android","IPhone","WindowsMobile","Blackberry",
"WebOS","Ubuntu","Windows7","Max OS X"};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
prepArray();
//Display List on Activity
ArrayAdapter adapter = new ArrayAdapter<String>(this,
R.layout.activity_listview, mobileArray);
ListView listView = (ListView) findViewById(R.id.mobile_list);
listView.setAdapter(adapter);
}
//Get list of strings from CSV ready to use
private void prepArray() {
InputStream inputStream = getResources().openRawResource(R.raw.strings);
CSVFile csvFile = new CSVFile(inputStream);
List myList = csvFile.read();
//This is where it has an error
//Set first array in myList to this new array myArray
String[] myArray = myList.get(0);
}
}
我实际上还没有设置mobileArray数组.现在,我只是想从List对象myList中提取"信息.
I'm not actually to the point of setting the mobileArray array yet. Right now I'm just trying to "extract" the information out of the List object myList...
有人可以向我解释这是怎么做的吗?也许我只是不完全了解List类型.似乎在CSVFile读取方法中返回resultList时,它作为由String数组对象组成的List对象返回.但是我似乎无法让它那样工作.
Can someone explain to me how this is done? Maybe I'm just not understanding the List type completely. It seems like when resultList is returned in the CSVFile read method, it's returned as an List object consisting of String array objects. But I can't seem to get it to work like that.
感谢您的帮助!
最终编辑(工作代码)
private void prepArray() {
try{
CSVReader reader = new CSVReader(new InputStreamReader(getResources().openRawResource(R.raw.strings)));//Specify asset file name
String [] nextLine;
while ((nextLine = reader.readNext()) != null) {
// nextLine[] is an array of values from the line
System.out.println(nextLine[0] + nextLine[1] + "etc...");
Log.d("VariableTag", nextLine[0]);
}
}catch(Exception e){
e.printStackTrace();
Toast.makeText(this, "The specified file was not found", Toast.LENGTH_SHORT).show();
}
}
编辑
现在,我的prepArray函数如下所示:
Now my prepArray function looks like the following:
private void prepArray() {
try{
String csvfileString = this.getApplicationInfo().dataDir + File.separatorChar + "strings.csv"
File csvfile = new File(csvfileString);
CSVReader reader = new CSVReader(new FileReader("csvfile.getAbsolutePath()"));
String [] nextLine;
while ((nextLine = reader.readNext()) != null) {
// nextLine[] is an array of values from the line
System.out.println(nextLine[0] + nextLine[1] + "etc...");
}
}catch(FileNotFoundException e){
e.printStackTrace();
Toast.makeText(this, "The specified file was not found", Toast.LENGTH_SHORT).show();
}
}
仍然产生FileNotFoundException.
Still produces the FileNotFoundException.
编辑2/3
这是当我在实际电话上运行应用程序时生成的日志,其中string.csv位于字符串的子文件夹(src \ main \ assets \ strings \ strings.csv)中,其中包含您请求的代码更改:
Here's the log that's produced when I run the app on an actual phone with the strings.csv in a subfolder of strings (src\main\assets\strings\strings.csv) with the change you requested to the code:
03/27 17:44:01: Launching app
$ adb push C:\Users\Roy\AndroidStudioProjects\ListDisplay\app\build\outputs\apk\app-debug.apk /data/local/tmp/com.yourtechwhiz.listdisplay
$ adb shell pm install -r "/data/local/tmp/com.yourtechwhiz.listdisplay"
pkg: /data/local/tmp/com.yourtechwhiz.listdisplay
Success
$ adb shell am start -n "com.yourtechwhiz.listdisplay/com.yourtechwhiz.listdisplay.MainActivity" -a android.intent.action.MAIN -c android.intent.category.LAUNCHER -D
Connecting to com.yourtechwhiz.listdisplay
D/HyLog: I : /data/font/config/sfconfig.dat, No such file or directory (2)
D/HyLog: I : /data/font/config/dfactpre.dat, No such file or directory (2)
D/HyLog: I : /data/font/config/sfconfig.dat, No such file or directory (2)
W/ActivityThread: Application com.yourtechwhiz.listdisplay is waiting for the debugger on port 8100...
I/System.out: Sending WAIT chunk
I/dalvikvm: Debugger is active
I/System.out: Debugger has connected
I/System.out: waiting for debugger to settle...
Connected to the target VM, address: 'localhost:8609', transport: 'socket'
I/System.out: waiting for debugger to settle...
I/System.out: waiting for debugger to settle...
I/System.out: waiting for debugger to settle...
I/System.out: waiting for debugger to settle...
I/System.out: waiting for debugger to settle...
I/System.out: waiting for debugger to settle...
I/System.out: waiting for debugger to settle...
I/System.out: debugger has settled (1498)
I/dalvikvm: Could not find method android.view.Window$Callback.onProvideKeyboardShortcuts, referenced from method android.support.v7.view.WindowCallbackWrapper.onProvideKeyboardShortcuts
W/dalvikvm: VFY: unable to resolve interface method 16152: Landroid/view/Window$Callback;.onProvideKeyboardShortcuts (Ljava/util/List;Landroid/view/Menu;I)V
D/dalvikvm: VFY: replacing opcode 0x72 at 0x0002
W/dalvikvm: VFY: unable to find class referenced in signature (Landroid/view/SearchEvent;)
I/dalvikvm: Could not find method android.view.Window$Callback.onSearchRequested, referenced from method android.support.v7.view.WindowCallbackWrapper.onSearchRequested
W/dalvikvm: VFY: unable to resolve interface method 16154: Landroid/view/Window$Callback;.onSearchRequested (Landroid/view/SearchEvent;)Z
D/dalvikvm: VFY: replacing opcode 0x72 at 0x0002
I/dalvikvm: Could not find method android.view.Window$Callback.onWindowStartingActionMode, referenced from method android.support.v7.view.WindowCallbackWrapper.onWindowStartingActionMode
W/dalvikvm: VFY: unable to resolve interface method 16158: Landroid/view/Window$Callback;.onWindowStartingActionMode (Landroid/view/ActionMode$Callback;I)Landroid/view/ActionMode;
D/dalvikvm: VFY: replacing opcode 0x72 at 0x0002
I/dalvikvm: Could not find method android.content.res.TypedArray.getChangingConfigurations, referenced from method android.support.v7.widget.TintTypedArray.getChangingConfigurations
W/dalvikvm: VFY: unable to resolve virtual method 455: Landroid/content/res/TypedArray;.getChangingConfigurations ()I
D/dalvikvm: VFY: replacing opcode 0x6e at 0x0002
I/dalvikvm: Could not find method android.content.res.TypedArray.getType, referenced from method android.support.v7.widget.TintTypedArray.getType
W/dalvikvm: VFY: unable to resolve virtual method 477: Landroid/content/res/TypedArray;.getType (I)I
D/dalvikvm: VFY: replacing opcode 0x6e at 0x0008
I/dalvikvm: Could not find method android.widget.FrameLayout.startActionModeForChild, referenced from method android.support.v7.widget.ActionBarContainer.startActionModeForChild
W/dalvikvm: VFY: unable to resolve virtual method 16589: Landroid/widget/FrameLayout;.startActionModeForChild (Landroid/view/View;Landroid/view/ActionMode$Callback;I)Landroid/view/ActionMode;
D/dalvikvm: VFY: replacing opcode 0x6f at 0x0002
I/dalvikvm: Could not find method android.content.Context.getColorStateList, referenced from method android.support.v7.content.res.AppCompatResources.getColorStateList
W/dalvikvm: VFY: unable to resolve virtual method 269: Landroid/content/Context;.getColorStateList (I)Landroid/content/res/ColorStateList;
D/dalvikvm: VFY: replacing opcode 0x6e at 0x0006
I/dalvikvm: Could not find method android.content.res.Resources.getDrawable, referenced from method android.support.v7.widget.ResourcesWrapper.getDrawable
W/dalvikvm: VFY: unable to resolve virtual method 418: Landroid/content/res/Resources;.getDrawable (ILandroid/content/res/Resources$Theme;)Landroid/graphics/drawable/Drawable;
D/dalvikvm: VFY: replacing opcode 0x6e at 0x0002
I/dalvikvm: Could not find method android.content.res.Resources.getDrawableForDensity, referenced from method android.support.v7.widget.ResourcesWrapper.getDrawableForDensity
W/dalvikvm: VFY: unable to resolve virtual method 420: Landroid/content/res/Resources;.getDrawableForDensity (IILandroid/content/res/Resources$Theme;)Landroid/graphics/drawable/Drawable;
D/dalvikvm: VFY: replacing opcode 0x6e at 0x0002
E/dalvikvm: Could not find class 'android.graphics.drawable.RippleDrawable', referenced from method android.support.v7.widget.AppCompatImageHelper.hasOverlappingRendering
W/dalvikvm: VFY: unable to resolve instanceof 140 (Landroid/graphics/drawable/RippleDrawable;) in Landroid/support/v7/widget/AppCompatImageHelper;
D/dalvikvm: VFY: replacing opcode 0x20 at 0x000c
W/System.err: java.io.FileNotFoundException: /csvfile.getAbsolutePath(): open failed: ENOENT (No such file or directory)
W/System.err: at libcore.io.IoBridge.open(IoBridge.java:462)
W/System.err: at java.io.FileInputStream.<init>(FileInputStream.java:78)
W/System.err: at java.io.FileInputStream.<init>(FileInputStream.java:105)
W/System.err: at java.io.FileReader.<init>(FileReader.java:66)
W/System.err: at com.yourtechwhiz.listdisplay.MainActivity.prepArray(MainActivity.java:43)
W/System.err: at com.yourtechwhiz.listdisplay.MainActivity.onCreate(MainActivity.java:26)
W/System.err: at android.app.Activity.performCreate(Activity.java:5287)
W/System.err: at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1087)
W/System.err: at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2145)
W/System.err: at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2231)
W/System.err: at android.app.ActivityThread.access$700(ActivityThread.java:139)
W/System.err: at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1401)
W/System.err: at android.os.Handler.dispatchMessage(Handler.java:102)
W/System.err: at android.os.Looper.loop(Looper.java:137)
W/System.err: at android.app.ActivityThread.main(ActivityThread.java:5082)
W/System.err: at java.lang.reflect.Method.invokeNative(Native Method)
W/System.err: at java.lang.reflect.Method.invoke(Method.java:515)
W/System.err: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:782)
W/System.err: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:598)
W/System.err: at dalvik.system.NativeStart.main(Native Method)
W/System.err: Caused by: libcore.io.ErrnoException: open failed: ENOENT (No such file or directory)
W/System.err: at libcore.io.Posix.open(Native Method)
W/System.err: at libcore.io.BlockGuardOs.open(BlockGuardOs.java:110)
W/System.err: at libcore.io.IoBridge.open(IoBridge.java:446)
W/System.err: ... 19 more
I/Adreno-EGL: <qeglDrvAPI_eglInitialize:385>: EGL 1.4 QUALCOMM build: ()
OpenGL ES Shader Compiler Version: E031.24.00.01
Build Date: 12/27/13 Fri
Local Branch: qualcomm_only
Remote Branch:
Local Patches:
Reconstruct Branch:
D/OpenGLRenderer: Enabling debug mode 0
D/OpenGLRenderer: GL error from OpenGLRenderer: 0x502
E/OpenGLRenderer: GL_INVALID_OPERATION
推荐答案
尝试 OpenCSV -它将使您的生活更轻松.
Try OpenCSV - it will make your life easier.
首先,按如下所示将此包添加到您的gradle
依赖项中
First, add this package to your gradle
dependencies as follows
implementation 'com.opencsv:opencsv:4.6'
那你就可以做
import com.opencsv.CSVReader;
import java.io.IOException;
import java.io.FileReader;
...
try {
CSVReader reader = new CSVReader(new FileReader("yourfile.csv"));
String[] nextLine;
while ((nextLine = reader.readNext()) != null) {
// nextLine[] is an array of values from the line
System.out.println(nextLine[0] + nextLine[1] + "etc...");
}
} catch (IOException e) {
}
或
CSVReader reader = new CSVReader(new FileReader("yourfile.csv"));
List myEntries = reader.readAll();
评论后编辑
try {
File csvfile = new File(Environment.getExternalStorageDirectory() + "/csvfile.csv");
CSVReader reader = new CSVReader(new FileReader(csvfile.getAbsolutePath()));
String[] nextLine;
while ((nextLine = reader.readNext()) != null) {
// nextLine[] is an array of values from the line
System.out.println(nextLine[0] + nextLine[1] + "etc...");
}
} catch (Exception e) {
e.printStackTrace();
Toast.makeText(this, "The specified file was not found", Toast.LENGTH_SHORT).show();
}
如果要与应用程序打包.csv
文件,并在安装应用程序时将其安装在内部存储中,请在项目src/main
文件夹(例如c:\myapp\app\src\main\assets\
)中创建一个assets
文件夹,并将.csv
文件放在其中,然后在您的活动中像这样引用它:
If you want to package the .csv
file with the application and have it install on the internal storage when the app installs, create an assets
folder in your project src/main
folder (e.g., c:\myapp\app\src\main\assets\
), and put the .csv
file in there, then reference it like this in your activity:
String csvfileString = this.getApplicationInfo().dataDir + File.separatorChar + "csvfile.csv"
File csvfile = new File(csvfileString);
这篇关于在Android App中读取CSV文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!