想了解超出最大缓存大小时的数据库行为
在大量使用电子邮件数据库后(有超过 1000 封邮件),电子邮件应用程序崩溃了。如果我再次返回应用程序,所有邮件都会开始自动删除。
获取到的错误日志如下:
E/AndroidRuntime( 417): java.lang.OutOfMemoryError
E/AndroidRuntime( 417): at java.lang.String.<init>(String.java:468)
E/AndroidRuntime( 417): at java.lang.AbstractStringBuilder.toString(AbstractStringBuilder.java:659)
E/AndroidRuntime( 417): at java.lang.StringBuilder.toString(StringBuilder.java:664)
E/AndroidRuntime( 417): at com.android.email.mail.transport.DiscourseLogger.addReceivingLineToBuffer(DiscourseLogger.java:57)
E/AndroidRuntime( 417): at com.android.email.mail.transport.DiscourseLogger.addReceivedByte(DiscourseLogger.java:70)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readByte(ImapResponseParser.java:71)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.expect(ImapResponseParser.java:332)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.parseToken(ImapResponseParser.java:199)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readToken(ImapResponseParser.java:165)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readTokens(ImapResponseParser.java:141)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readResponse(ImapResponseParser.java:92)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapStore$ImapConnection.readResponse(ImapStore.java:1491)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapStore$ImapFolder.fetchInternal(ImapStore.java:887)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapStore$ImapFolder.fetch(ImapStore.java:810)
E/AndroidRuntime( 417): at com.android.email.MessagingController.synchronizeMailboxGeneric(MessagingController.java:898)
E/AndroidRuntime( 417): at com.android.email.MessagingController.synchronizeMailboxSynchronous(MessagingController.java:396)
E/AndroidRuntime( 417): at com.android.email.MessagingController.access$2(MessagingController.java:384)
E/AndroidRuntime( 417): at com.android.email.MessagingController$2.run(MessagingController.java:372)
E/AndroidRuntime( 417): at com.android.email.MessagingController.run(MessagingController.java:171)
E/AndroidRuntime( 417): at java.lang.Thread.run(Thread.java:1096)
W/Database(497):已达到数据库 /data/data/com.android.email/databases/EmailProvider.db 的编译 SQL 语句缓存的最大大小;即,缓存中没有此 sql 语句的空间:SELECT _id FROM Attachment WHERE messageKey=996。请更改您的 sql 语句以使用“?”对于bindargs,而不是使用实际值
想知道出现上述错误的行为是什么。
我的意思是,如果超过最大缓存大小,android 会做什么?如果您能知道在哪里实现了这一点,那将会非常有帮助。
After extensive use of Email database (there were more than 1000 mails), Email App crashed. If i come back to App again all mails started deleting automatically.
The error logs obtained are as below:
E/AndroidRuntime( 417): java.lang.OutOfMemoryError
E/AndroidRuntime( 417): at java.lang.String.<init>(String.java:468)
E/AndroidRuntime( 417): at java.lang.AbstractStringBuilder.toString(AbstractStringBuilder.java:659)
E/AndroidRuntime( 417): at java.lang.StringBuilder.toString(StringBuilder.java:664)
E/AndroidRuntime( 417): at com.android.email.mail.transport.DiscourseLogger.addReceivingLineToBuffer(DiscourseLogger.java:57)
E/AndroidRuntime( 417): at com.android.email.mail.transport.DiscourseLogger.addReceivedByte(DiscourseLogger.java:70)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readByte(ImapResponseParser.java:71)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.expect(ImapResponseParser.java:332)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.parseToken(ImapResponseParser.java:199)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readToken(ImapResponseParser.java:165)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readTokens(ImapResponseParser.java:141)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapResponseParser.readResponse(ImapResponseParser.java:92)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapStore$ImapConnection.readResponse(ImapStore.java:1491)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapStore$ImapFolder.fetchInternal(ImapStore.java:887)
E/AndroidRuntime( 417): at com.android.email.mail.store.ImapStore$ImapFolder.fetch(ImapStore.java:810)
E/AndroidRuntime( 417): at com.android.email.MessagingController.synchronizeMailboxGeneric(MessagingController.java:898)
E/AndroidRuntime( 417): at com.android.email.MessagingController.synchronizeMailboxSynchronous(MessagingController.java:396)
E/AndroidRuntime( 417): at com.android.email.MessagingController.access$2(MessagingController.java:384)
E/AndroidRuntime( 417): at com.android.email.MessagingController$2.run(MessagingController.java:372)
E/AndroidRuntime( 417): at com.android.email.MessagingController.run(MessagingController.java:171)
E/AndroidRuntime( 417): at java.lang.Thread.run(Thread.java:1096)
W/Database( 497): Reached MAX size for compiled-sql statement cache for database /data/data/com.android.email/databases/EmailProvider.db; i.e., NO space for this sql statement in cache: SELECT _id FROM Attachment WHERE messageKey=996. Please change your sql statements to use '?' for bindargs, instead of using actual values
I want to know what is the behavior that I get the above error.
I mean what will android do if the Maximum cache size is exceeded? If you could tell where the implementation for that is done, it will be very helpful.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
这是另一个问题。这条消息说明了一切:
“数据库的已编译 SQL 语句缓存已达到最大大小”
基本上,电子邮件应用程序在查询中使用硬编码值。相反,它应该使用准备好的语句,以便仅缓存准备好的语句。
希望有帮助。
this is another issue. This message says it all:
"Reached MAX size for compiled-sql statement cache for database"
basically the emaill application is using hardcoded values in the queries. Instead it should use prepared statements in order to cache only the prepared statements.
Hope it helps.
您可以使用
setMaximumSize
设置最大数据库大小。您可以使用 getMaximumSiz 让线程检查数据库大小,看看这是否接近您之前修复的数据库大小。
然后将本地数据库复制(复制)到SD卡上的数据库并使用releaseMemory释放内存。
You have a way to set Max DB Size using
setMaximumSize
.You can have a thread checking the DB Size using
getMaximumSiz
and if this is near to the DB size you have fixed before.Then replicate(copy) your local DB to DB on SD card and release the memory using releaseMemory.