Silverlight XAML与Code-behind相比

时间:2010-07-15 03:55:21

标签: silverlight xaml

从编译代码的纯粹速度角度来看,如果我使用100%XAML或100%代码隐藏或其间的某种组合,它会有所不同吗?代码隐藏中没有像if语句那样的逻辑 - 它与XAML将加载内容元素的操作完全相同。

如果它确实有所作为,我怎么能测试它在速度方面有多大差异?

3 个答案:

答案 0 :(得分:5)

在Silverlight中,XAML在运行时被解析。

因为在XAML中定义的对象的实例化比在代码中定义的对象慢。

我编写了一个非常简单的测试,并且在我的测试实例化中,通过编译代码实现对象的速度比解析Xaml快4倍。

Silverlight中的.g.cs文件用于使用x:Name属性声明在XAML中定义的字段。

它也用于调用XAML解析器并在此之后填充字段。

请在回复结束时查看.g.cs的示例。

按照我非常简单的测试代码:

的MainPage:

<UserControl x:Class="SilverlightXamlVsCode.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
  <StackPanel Orientation="Vertical">
        <Button
            Content="Start Xaml"
            Width="150"
            Height="27"
            Click="OnStartXaml" />
        <TextBlock
            x:Name="_startTimeXaml" />
        <TextBlock
            x:Name="_endTimeXaml" />
        <TextBlock
            x:Name="_durationXaml" />

        <ContentControl
            x:Name="_content" />
        <Button
            Content="Start Code"
            Width="150"
            Height="27"
            Click="OnStartCode" />
        <TextBlock
            x:Name="_startTimeCode" />
        <TextBlock
            x:Name="_endTimeCode" />
        <TextBlock
            x:Name="_durationCode" />
    </StackPanel>
</UserControl>

背后的各个MainPage代码:

using System;
using System.Windows;
using System.Windows.Controls;

namespace SilverlightXamlVsCode
{
    public partial class MainPage : UserControl
    {
        public MainPage()
        {
            InitializeComponent();
        }

        private void OnStartCode(object sender, RoutedEventArgs e)
        {
            var startTime = DateTime.Now;
            _startTimeCode.Text = startTime.ToString();
            for (int i = 0; i < 10000; i++)
            {
                _content.Content = new Button() {Width = 100, Height = 27, Content = "Code"};
            }
            var endTime = DateTime.Now;
            _endTimeCode.Text = endTime.ToString();

            var duration = endTime - startTime;
            _durationCode.Text = duration.TotalSeconds.ToString();

        }

        private void OnStartXaml(object sender, RoutedEventArgs e)
        {
            var startTime = DateTime.Now;
            _startTimeXaml.Text = startTime.ToString();
            for (int i = 0; i < 10000; i++)
            {
                _content.Content = new SilverlightControl1();
            }
            var endTime = DateTime.Now;
            _endTimeXaml.Text = endTime.ToString();

            var duration = endTime - startTime;
            _durationXaml.Text = duration.TotalSeconds.ToString();            
        }
    }
}

Xaml中的一个非常小的控件:

<Button x:Class="SilverlightXamlVsCode.SilverlightControl1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    Width="100" Height="27" Content="Xaml">
</Button>

代码背后:

using System.Windows.Controls;

namespace SilverlightXamlVsCode
{
    public partial class SilverlightControl1 : Button
    {
        public SilverlightControl1()
        {
            InitializeComponent();
        }
    }
}

====

请参阅下面的.g.cs示例:

#pragma checksum "C:\Workspace\Playplace\SilverlightXamlVsCode\SilverlightXamlVsCode\MainPage.xaml"
//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a tool.
//     Runtime Version:2.0.50727.3603
//
//     Changes to this file may cause incorrect behavior and will be lost if
//     the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

using System;
using System.Windows;
using System.Windows.Automation;
using System.Windows.Automation.Peers;
using System.Windows.Automation.Provider;
using System.Windows.Controls;
using System.Windows.Controls.Primitives;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Interop;
using System.Windows.Markup;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Media.Imaging;
using System.Windows.Resources;
using System.Windows.Shapes;
using System.Windows.Threading;
namespace SilverlightXamlVsCode 
{
    public partial class MainPage : System.Windows.Controls.UserControl {
        internal System.Windows.Controls.TextBlock _startTimeXaml;
        internal System.Windows.Controls.TextBlock _endTimeXaml;
        internal System.Windows.Controls.TextBlock _durationXaml;
        internal System.Windows.Controls.ContentControl _content;
        internal System.Windows.Controls.TextBlock _startTimeCode;
        internal System.Windows.Controls.TextBlock _endTimeCode;
        internal System.Windows.Controls.TextBlock _durationCode;
        private bool _contentLoaded;

        /// <summary>
        /// InitializeComponent
        /// </summary>
        [System.Diagnostics.DebuggerNonUserCodeAttribute()]
        public void InitializeComponent() {
            if (_contentLoaded) {
                return;
            }
            _contentLoaded = true;

            // INVOKE XAML PARSER HERE
            System.Windows.Application.LoadComponent(this, new System.Uri("/SilverlightXamlVsCode;component/MainPage.xaml", System.UriKind.Relative));

            this._startTimeXaml = ((System.Windows.Controls.TextBlock)(this.FindName("_startTimeXaml")));
            this._endTimeXaml = ((System.Windows.Controls.TextBlock)(this.FindName("_endTimeXaml")));
            this._durationXaml = ((System.Windows.Controls.TextBlock)(this.FindName("_durationXaml")));
            this._content = ((System.Windows.Controls.ContentControl)(this.FindName("_content")));
            this._startTimeCode = ((System.Windows.Controls.TextBlock)(this.FindName("_startTimeCode")));
            this._endTimeCode = ((System.Windows.Controls.TextBlock)(this.FindName("_endTimeCode")));
            this._durationCode = ((System.Windows.Controls.TextBlock)(this.FindName("_durationCode")));
        }
    }
}

答案 1 :(得分:2)

您不太可能在两者之间看到很多性能差异,因为XAML最终会转换为代码并进行编译。通过将所有UI放入纯代码中,您将失去XAML作为以UI为中心的域特定语言提供的优势。重要的是要保持关注点的分离,并将UI布局和样式与驱动UI的代码分开(并且进一步保持这两者与业务逻辑分离),从而生成更易于维护的应用程序。

XAML是一款出色的UI构建工具......比纯代码更适合工作。我建议您以XAML格式保留UI布局和样式。

如果您想了解有关如何构建XAML的更多信息,建议您阅读以下内容:

Building a WPF Application (WPF)

使用WPF,您可以在编译XAML时获得两个生成的文件:表示UI行为的.g.cs文件和.baml文件,它是XAML节点层次结构的紧凑二进制表示形式。使用Silverlight,您可以在.g.cs(或.g.vb)文件中获取生成的代码,但是您没有获得BAML。虽然最终的结果是任何行为都被编译,但是使用Silverlight,您仍然会遇到包含UI节点层次结构的XML文件,而不是更紧凑的二进制表示。 (不确定为什么会这样,Silverlight浏览器控件的限制或可能有限的.NET框架。)

答案 2 :(得分:0)

我试图复制克林格答案的基准调查结果。我发现他的基准测试不能准确测量时间,因为Silverlight直到OnClick函数返回后才进行任何渲染,这意味着在计时器停止计数之前,实际上没有进行任何模板解析或更复杂的XAML工作。我目前没有更好的计时解决方案。

实际标记为正式答案的答案仅适用于WPF。在Silverlight中,XAML不会转换为已编译的代码。