在 Flex 中迭代 dataProvider

发布于 2024-10-05 06:40:05 字数 2586 浏览 0 评论 0原文

我想知道...我想在基于 DropDownList 的组件中迭代 dataProvider。 首先,它不起作用(它编译了,但从未迭代):

var o:Object;
for each (var o:Object in dataProvider)
{
}

我猜它不起作用是因为 IList 不提供对象,或者有人能够轻松解释的东西。

我尝试了一些从效率角度来看看起来很糟糕的方法,但它确实有效。就是这样:

for (var i:int = 0; i < dataProvider.length; i++)
{
   o = dataProvider.getItemAt(i);
}

但这太可怕了,我很想在这里询问另一种可能的解决方案。

更新:

我会尝试详细说明...我正在制作(嗯,它已经制作了)一个组件,就像 DropDownList 一样,是可绑定的,而不是索引(如 selectedIndex="@{variable}") ,而是 ArrayCollection 内部变量的值。

假设您有一个包含两个对象的 dataProvider: {a:'5', nmb:' Five', blabla:'cinco'}{a:'39', nmb:'三十九',blabla:'treinta y nueve'}

该组件,如果这样声明:

<com:ddListN idxName="a" selectedN="@{val}" labelField="nmb">

是否使用 val 将 DropDownList 设置/获取到正确的索引,将该值与 idxName 中定义的变量进行比较。

好吧,这是整个代码(没那么多):

<?xml version="1.0" encoding="utf-8"?>
<s:DropDownList xmlns:fx="http://ns.adobe.com/mxml/2009" 
                xmlns:s="library://ns.adobe.com/flex/spark" 
                xmlns:mx="library://ns.adobe.com/flex/mx"
                change="ch()">
    <fx:Declarations>
    </fx:Declarations>
    <fx:Script>
        <![CDATA[
            private var _selectedN:String;

            public var idxName:String = 'n';

            [Bindable(event="changeSelected")]
            public function get selectedN():String
            {
                return this.selectedItem[idxName];
            }

            public function set selectedN(v:String):void
            {
                var o:Object;
//              for each (var o:Object in dataProvider) @@
                for (var i:int = 0; i < this.dataProvider.length; i++)
                {
                    o = dataProvider.getItemAt(i);
                    if (o[idxName] == v)
                    {
                        this.selectedIndex = i;
                        _selectedN = v;
                        dispatchEvent(new Event("changeSelected"));
                        return; 
                    }

                }
                this.selectedItem = null; // no seleccionar nada (@@?)
                _selectedN = null;
                dispatchEvent(new Event("changeSelected"));
            }

            private function ch():void
            {
                _selectedN = this.selectedItem[idxName];
                dispatchEvent(new Event("changeSelected"));
            }
        ]]>
    </fx:Script>
</s:DropDownList>

I'm wondering... I want to iterate through a dataProvider, in a Component which is based on a DropDownList.
First thing, that it didn't work (it compiled, but never iterated), was:

var o:Object;
for each (var o:Object in dataProvider)
{
}

I guess it didn't work because a IList doesn't provide Objects, or something someone would be able to explain easily.

I tried something that looks horrible from a efficiency perspective, nonetheless it works. This is it:

for (var i:int = 0; i < dataProvider.length; i++)
{
   o = dataProvider.getItemAt(i);
}

But it is so horrible that I felt tempted to ask here about another possible solution.

UPDATE:

I'll try to elaborate... I'm making (well, it is made already) a component that, being like a DropDownList, is bindable, not to an index (like selectedIndex="@{variable}"), but to a value of a variable inside of the ArrayCollection.

Say, you have a dataProvider with two objects: {a:'5', nmb:'five', blabla:'cinco'} and {a:'39', nmb:'thirty-nine', blabla:'treinta y nueve'}.

This component, if declared like this:

<com:ddListN idxName="a" selectedN="@{val}" labelField="nmb">

Does use val to set/get the DropDownList to the proper index, comparing the value with the variable defined in idxName.

Well, this is the entire code (is not that much):

<?xml version="1.0" encoding="utf-8"?>
<s:DropDownList xmlns:fx="http://ns.adobe.com/mxml/2009" 
                xmlns:s="library://ns.adobe.com/flex/spark" 
                xmlns:mx="library://ns.adobe.com/flex/mx"
                change="ch()">
    <fx:Declarations>
    </fx:Declarations>
    <fx:Script>
        <![CDATA[
            private var _selectedN:String;

            public var idxName:String = 'n';

            [Bindable(event="changeSelected")]
            public function get selectedN():String
            {
                return this.selectedItem[idxName];
            }

            public function set selectedN(v:String):void
            {
                var o:Object;
//              for each (var o:Object in dataProvider) @@
                for (var i:int = 0; i < this.dataProvider.length; i++)
                {
                    o = dataProvider.getItemAt(i);
                    if (o[idxName] == v)
                    {
                        this.selectedIndex = i;
                        _selectedN = v;
                        dispatchEvent(new Event("changeSelected"));
                        return; 
                    }

                }
                this.selectedItem = null; // no seleccionar nada (@@?)
                _selectedN = null;
                dispatchEvent(new Event("changeSelected"));
            }

            private function ch():void
            {
                _selectedN = this.selectedItem[idxName];
                dispatchEvent(new Event("changeSelected"));
            }
        ]]>
    </fx:Script>
</s:DropDownList>

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

寄人书 2024-10-12 06:40:05

实际上,for every 循环比普通 for 循环慢一点。看看关于 VS Foreach on Array 性能的答案< /a>.

要回答您的问题,为什么您的 for every 循环不起作用。不幸的是,这种类型的循环仅适用于某些类型的类。据我所知,这些是:

  • Array
  • Vector
  • XML
  • XMLList
  • 和扩展 Proxy 的类code> 实现 foreach 循环所需的函数。我只知道 ListCollectionView 及其子类 ArrayCollectionXMLListCollection

ArrayList 这样的集合类不能与 foreach 循环一起使用,因为它们不是 Flash Player 中的本机对象(例如 Array),并且它们不扩展 Proxy 类。

因此,您能做的最好的事情就是使用简单的 for 循环,这些循环甚至比 foreach 循环更快。

Actually for each loops are a little bit slower than normal for loops. Take a look at the answer to For VS Foreach on Array performance.

To answer your question, why your for each loop doesn`t work. Unfortunatly this type of loop works only for certain types of classes. As far as I know those are:

  • Array
  • Vector
  • XML
  • XMLList
  • and classes that extend Proxy that implement the functions needed for for each loops. ListCollectionView and its subclasses ArrayCollection and XMLListCollection are the only ones I know of.

Collection classes like ArrayList do not work with for each loops since they are not native objects in Flash Player (like Array) and they don't extend the Proxy class.

So, the best thing you can do is to use simple for loops and those loops are even faster than the for each loops.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文