简单易懂的问题,希望能有类似的简单解决方案:
当我输入我的搜索查询时,我有时会在dataField = new ArrayCollection(result.data);
行上收到“错误#1009无法访问空对象引用的属性或方法”。
AS3:
private function getSearch():void
{
//status = "Loading data";
selectStmt = new SQLStatement();
selectStmt.sqlConnection = conn;
var sql:String = "SELECT [Index], Title, CAST(Picture AS ByteArray) AS Picture FROM Data WHERE Title LIKE @searchTarget";
selectStmt.parameters["@searchTarget"] = "%" + searchTarget + "%";
selectStmt.text = sql;
selectStmt.addEventListener(SQLEvent.RESULT, selectResult2);
selectStmt.addEventListener(SQLErrorEvent.ERROR, selectError);
selectStmt.execute();
targetRecordId = pngIndex;
}
private function selectResult2(event:SQLEvent):void
{
//status = "Data loaded";
selectStmt.removeEventListener(SQLEvent.RESULT, selectResult);
selectStmt.removeEventListener(SQLErrorEvent.ERROR, selectError);
var result:SQLResult = selectStmt.getResult();
dataField = new ArrayCollection(result.data);
if (result.data != null) {
pngIndex = result.data.Index;
pngTitle = result.data.Title;
pngByteArray = result.data.Picture;
targetRecordId = pngIndex;
}
}
MXML:
<s:List id="myList"
x="0" y="40"
width="100%" height="100%"
labelField="Title"
dataProvider="{dataField}"
change="myList_changeHandler(event)"
>
</s:List>
我尝试过的事情(包括这些解决方案的排列):
1)在SelectResult2方法中移动错误代码
2)添加if (result.data == null)
方法
3)使用Array而不是ArrayCollection(我发现有人发现这在某个论坛的某个地方适用于他们的项目)
4)添加计时器功能以尝试限制数据库搜索的频率。 (虽然我认为这是最好的解决方案,但我想我必须再试一次)
请注意,从我所知道的错误发生,主要是因为过快地输入搜索字符
感谢您的帮助。
答案 0 :(得分:0)
首先,怎么样
if(result == null)
return;
此外,计时器是一个好主意,通常大约半秒钟,这样就可以在用户输入时对您的数据库进行锤击。
private var timer:Timer = new Timer(500, 1);
protected function textChangeHandler():void{
timer.reset();
timer.addEventListener(TimerEvent.Timer, getSearch);//Could be moved to a creation complete
timer.start();
}
错误处理并根据需要删除/添加事件。您也可以禁用搜索,直到最后一个完成,这与计时器一起不应该侵扰用户。
答案 1 :(得分:0)
<强> 1。使用响应者
您对数据库的每次调用都使用相同的事件处理函数。因此,当函数执行时,它可能已经丢失了对其原始语句的引用(因为在此期间启动了新的调用)。这就是为什么你在结果对象上得到那些无效点。
所以抛弃事件监听器并改为使用Responder,如下所示:
var stmt:SQLStatement = new SQLStatement();
stmt.sqlConnection = connection;
stmt.text = query;
var resp:Responder = new Responder(onResult, onFail);
stmt.execute(-1, resp);
'onResult'函数将SQLResult对象作为单个参数,您不再需要引用原始语句来获得该结果。
<强> 2。延迟强>
使用计时器,是的。但是不要用它来间隔进行数据库调用。你不知道什么时候停止拨打这些电话,对吗?用它来检测用户是否还在打字:当它需要的时间超过 - 例如 - 300毫秒。对于一个KeyboardEvent.KEY_UP来到另一个,然后激活对数据库的调用。一次。
第3。使用阈值
不要只用一个字母开始查询。使用至少2-3个字符的阈值。无论如何,你不会得到任何一个字符的相关建议。阈值应该高多少,取决于要搜索的集合的大小。
<强> 4。过滤ArrayCollection
忽略以上所有内容。更简单的解决方案可能是将您要搜索的所有记录加载到ArrayCollection中,并使用filterFunction
仅显示与某个String匹配的记录。只要集合不是巨大的(如成千上万条记录),这种方法就可以了,并且实现起来更快。