我的ListView没有显示任何内容。
我从Hacker-News下载热门API并将它们放入我的应用程序中。我想把这些故事的标题放在我的列表视图中(它们超过100个)。
我下载它们并将它们存储在数据库中以进行永久存储,然后将它们添加到我的列表视图中,但NOTHING正在我的应用程序中显示。任何人都可以向我解释原因吗?
更新:我遇到了CursorIndexOutOfBoundException问题。 (索引350中的350)
public class MainActivity extends AppCompatActivity {
ListView listView;
private SQLiteDatabase myDatabase;
private Cursor cursor;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
listView = (ListView) findViewById(R.id.listView);
DownloadIDs ids = new DownloadIDs();
String URL = "https://hacker-news.firebaseio.com/v0/topstories.json?print=pretty";
ids.execute(URL);
try {
ArrayList<String> titles = new ArrayList<String>();
ArrayAdapter arrayAdapter = new ArrayAdapter(this, android.R.layout.simple_list_item_1, titles);
listView.setAdapter(arrayAdapter);
myDatabase = this.openOrCreateDatabase("HackerNews", MODE_PRIVATE, null);
Cursor cursor1 = myDatabase.rawQuery("SELECT * FROM ids", null);
int index = cursor1.getColumnIndex("urlID");
cursor1.moveToFirst();
while (cursor1 != null) {
String newUrl = "https://hacker-news.firebaseio.com/v0/item/" + cursor1.getString(index) + ".json?print=pretty";
new DownloadContent().execute(newUrl);
cursor1.moveToNext();
}
Cursor cursor2 = myDatabase.rawQuery("SELECT * FROM content", null);
int titleIndex = cursor2.getColumnIndex("title");
cursor2.moveToFirst();
titles.add("Hello");
while(cursor2 != null){
titles.add(cursor2.getString(titleIndex));
arrayAdapter.notifyDataSetChanged();
cursor2.moveToNext();
}
}catch (Exception e){
e.printStackTrace();
}
}
public class DownloadIDs extends AsyncTask<String, Void, String> {
@Override
protected String doInBackground(String... params) {
String result = "";
URL url;
HttpURLConnection urlConnection = null;
try {
url = new URL(params[0]);
urlConnection = (HttpURLConnection) url.openConnection();
InputStream inputStream = urlConnection.getInputStream();
InputStreamReader reader = new InputStreamReader(inputStream);
int data = reader.read();
while (data >= 0) {
char current = (char) data;
result += current;
data = reader.read();
}
return result;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
@Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
try {
myDatabase.execSQL("CREATE TABLE IF NOT EXISTS ids (id INTEGER PRIMARY KEY, urlID VARCHAR)");
cursor = myDatabase.rawQuery("SELECT COUNT(*) FROM ids", null);
cursor.moveToFirst();
int count = cursor.getInt(0);
if (!(count > 0)) {
JSONArray ids = new JSONArray(s);
for (int i = 0; i < ids.length(); i++) {
myDatabase.execSQL("INSERT INTO ids (urlID) VALUES ('" + ids.getString(i) + "')");
}
}
}catch (Exception e){
e.printStackTrace();
}
}
}
public class DownloadContent extends AsyncTask<String, Void, String> {
@Override
protected String doInBackground(String... params) {
String result = "";
URL url;
HttpURLConnection urlConnection = null;
try {
url = new URL(params[0]);
urlConnection = (HttpURLConnection) url.openConnection();
InputStream inputStream = urlConnection.getInputStream();
InputStreamReader reader = new InputStreamReader(inputStream);
int data = reader.read();
while (data >= 0) {
char current = (char) data;
result += current;
data = reader.read();
}
return result;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
@Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
try {
myDatabase.execSQL("CREATE TABLE IF NOT EXISTS content(id INTEGER PRIMARY KEY, title VARCHAR, url VARCHAR)");
cursor = myDatabase.rawQuery("SELECT COUNT(*) FROM content", null);
cursor.moveToFirst();
int count = cursor.getInt(0);
if (!(count > 0)) {
JSONObject jsonObject = new JSONObject(s);
String title = jsonObject.getString("title");
Log.i("title", title);
String url = jsonObject.getString("url");
Log.i("url", url);
myDatabase.execSQL("INSERT INTO content (title, url) VALUES('" + title + "','" + url + "')");
}
}catch(Exception e){
e.printStackTrace();
}
}
}
}
答案 0 :(得分:1)
知道了!我修好了它。我只是不得不减少新闻量(我决定选择前20个),我决定在我的应用程序上只运行一个ASyncTask。
以下是编辑过的代码:
PD:感谢@cabbabe1991,因为他给了我如何解决它的提示。谢谢!
public class MainActivity extends AppCompatActivity {
ListView listView;
private SQLiteDatabase myDatabase;
ArrayList<String> titles;
ArrayList<String> urls;
ArrayAdapter arrayAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
listView = (ListView) findViewById(R.id.listView);
titles = new ArrayList<>();
urls = new ArrayList<>();
arrayAdapter = new ArrayAdapter(this, android.R.layout.simple_list_item_1, titles);
listView.setAdapter(arrayAdapter);
try {
myDatabase = this.openOrCreateDatabase("HackerNews", MODE_PRIVATE, null);
DownloadTask downloadTask = new DownloadTask();
String URL = "https://hacker-news.firebaseio.com/v0/topstories.json?print=pretty";
downloadTask.execute(URL);
Cursor cursor = myDatabase.rawQuery("SELECT * FROM content", null);
int titleIndex = cursor.getColumnIndex("title");
int urlIndex = cursor.getColumnIndex("url");
cursor.moveToFirst();
while(cursor!=null){
titles.add(cursor.getString(titleIndex));
urls.add(cursor.getString(urlIndex));
cursor.moveToNext();
}
arrayAdapter.notifyDataSetChanged();
} catch (Exception e) {
e.printStackTrace();
}
listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Intent intent = new Intent(getApplicationContext(), MainActivity2.class);
MainActivity2.url = urls.get(position);
startActivity(intent);
}
});
}
public class DownloadTask extends AsyncTask<String, Void, String> {
@Override
protected String doInBackground(String... params) {
String articleInfo = "";
URL url;
HttpURLConnection urlConnection = null;
try {
url = new URL(params[0]);
urlConnection = (HttpURLConnection) url.openConnection();
InputStream inputStream = urlConnection.getInputStream();
InputStreamReader reader = new InputStreamReader(inputStream);
int data = reader.read();
while (data >= 0) {
char current = (char) data;
articleInfo += current;
data = reader.read();
}
//myDatabase.execSQL("CREATE TABLE IF NOT EXISTS ids (id INTEGER PRIMARY KEY, urlID VARCHAR)");
myDatabase.execSQL("CREATE TABLE IF NOT EXISTS content (id INTEGER PRIMARY KEY, title VARCHAR, url VARCHAR)");
myDatabase.delete("content", null, null);
JSONArray ids = new JSONArray(articleInfo);
for (int i = 0; i < 20; i++) {
//myDatabase.execSQL("INSERT INTO ids (urlID) VALUES ('" + ids.getString(i) + "')");
String articleInfo2 = "";
URL url2 = new URL("https://hacker-news.firebaseio.com/v0/item/" + ids.getString(i) + ".json?print=pretty");
HttpURLConnection urlConnection2 = (HttpURLConnection) url2.openConnection();
InputStream inputStream2 = urlConnection2.getInputStream();
InputStreamReader reader2 = new InputStreamReader(inputStream2);
int data2 = reader2.read();
while (data2 >= 0) {
char current2 = (char) data2;
articleInfo2 += current2;
data2 = reader2.read();
}
JSONObject jsonObject = new JSONObject(articleInfo2);
String title = "'" + jsonObject.getString("title").replaceAll("'", "") + "'";
String articleURL = "'" + jsonObject.getString("url") + "'";
myDatabase.execSQL("INSERT INTO content (title, url) VALUES (" + title + "," + articleURL + ")");
}
return null;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
@Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
}
}
}
答案 1 :(得分:0)
问题在于此代码
1)
Cursor cursor1 = myDatabase.rawQuery("SELECT * FROM ids", null);
int index = cursor1.getColumnIndex("urlID");
cursor1.moveToFirst();
while (cursor1 != null) {
String newUrl = "https://hacker-news.firebaseio.com/v0/item/" + cursor1.getString(index) + ".json?print=pretty";
new DownloadContent().execute(newUrl);
cursor1.moveToNext();
}
如何?
你说要光标来获取列索引,并从中获取项目ID,但是当数据库为空时,该值将为null。因此api不会返回响应。另外,你在游标中犯了同样的错误,如下所示。
2)。
int titleIndex = cursor2.getColumnIndex("title");
cursor2.moveToFirst();
titles.add("Hello");
while(cursor2 != null){
titles.add(cursor2.getString(titleIndex));
arrayAdapter.notifyDataSetChanged();
cursor2.moveToNext();
}
如何?
你说光标移动到第一条记录(moveToFirst()),如果当前没有记录则该怎么办。如果光标为空,则此方法返回false。因此,请确保此方法返回true,然后继续。
或强>
这样做(更好的方法)......
while(cursor.moveToNext()) {
//If inside , that means you are on the next record.Fetch the column values here
}
参考文献: Cursor methods