Javascript 在C#中是否存在敲除JS计算的等价物?
我使用了很多,我喜欢计算可观测的概念。Javascript 在C#中是否存在敲除JS计算的等价物?,javascript,c#,knockout.js,Javascript,C#,Knockout.js,我使用了很多,我喜欢计算可观测的概念。一个计算可观测的概念被定义为其他可观测的函数,它依赖于它内部使用的任何可观测变量。这允许出现非常有趣的场景,其中所有因变量在单个可观测变化时更新这会影响其他计算变量 问题:C#是否有使用标准库或开源库的等价物?答案:是的,有。 接口正在这样做,它位于System.ComponentModel命名空间中 此接口包含一个事件,该事件将在属性更改时触发 C#4及以下示例 public class DataCS4 : INotifyPropertyChanged
一个计算可观测的概念被定义为其他可观测的函数,它依赖于它内部使用的任何可观测变量。
这允许出现非常有趣的场景,其中所有因变量在单个可观测变化时更新这会影响其他计算变量
问题:C#是否有使用标准库或开源库的等价物?答案:是的,有。
接口正在这样做,它位于
System.ComponentModel
命名空间中此接口包含一个事件,该事件将在属性更改时触发 C#4及以下示例
public class DataCS4 : INotifyPropertyChanged
{
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged(string propertyName)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
handler(this, new PropertyChangedEventArgs(propertyName));
}
#endregion
// Represent an Observable
private int firstNumber;
public int FirstNumber
{
get { return firstNumber; }
set
{
if (value == firstNumber)
return;
this.firstNumber = value;
OnPropertyChanged("FirstNumber");
OnPropertyChanged("Sum");
}
}
// Represent an Observable
private int secondNumber;
public int SecondNumber
{
get { return secondNumber; }
set
{
if (value == secondNumber)
return;
this.secondNumber = value;
OnPropertyChanged("SecondNumber");
OnPropertyChanged("Sum");
}
}
// Represent Computed
public int Sum { get { return FirstNumber + SecondNumber; } }
}
这是两个整数求和的非常简单的示例我们有<代码>第一个数< /代码>属性,(我们可以把它看作是可观测的)。
我们也有<代码>第二号<代码>属性(我们可以把它看作是敲除可观察到的)
我们有<代码>和<代码>属性(我们可以把它看作是计算出来的)。 现在,每当我们更改
FirstNumber
或SecondNumber
(通过调用相应的set函数),我们都会通知所有订阅者这些属性(通过调用OnPropertyChanged
方法完成)另外,我们正在调用
Sum
属性的OnPropertyChanged
,以通知该属性的订阅者该属性的值已更改。注意这是使用WPF+MVVM模式时非常常见的模式 当使用C#5.0或C#6.0时,您可以从它们的新功能中获益,使代码更简单 C#5.0示例
public class DataCS5 : INotifyPropertyChanged
{
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged([CallerMemberName]string propertyName = null)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
handler(this, new PropertyChangedEventArgs(propertyName));
}
#endregion
// Represent an Observable
private int firstNumber;
public int FirstNumber
{
get { return firstNumber; }
set
{
if (value == firstNumber)
return;
this.firstNumber = value;
OnPropertyChanged();
OnPropertyChanged("Sum");
}
}
// Represent an Observable
private int secondNumber;
public int SecondNumber
{
get { return secondNumber; }
set
{
if (value == secondNumber)
return;
this.secondNumber = value;
OnPropertyChanged();
OnPropertyChanged("Sum");
}
}
// Represent Computed
public int Sum { get { return FirstNumber + SecondNumber; } }
}
这里有两个变化
protected virtual void OnPropertyChanged([CallerMemberName]string propertyName=null)
,因此通过将此属性放在方法的参数之前,编译器将自动知道调用此方法的属性的名称,而无需手动传递属性名称,因此我们可以编写以下语句OnPropertyChanged()代码>表示第二次修改
CallerMemberName
属性存在于System.Runtime.CompilerServices
命名空间中
C#6.0示例
public class DataCS5 : INotifyPropertyChanged
{
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged([CallerMemberName]string propertyName = null)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
handler(this, new PropertyChangedEventArgs(propertyName));
}
#endregion
// Represent an Observable
private int firstNumber;
public int FirstNumber
{
get { return firstNumber; }
set
{
if (value == firstNumber)
return;
this.firstNumber = value;
OnPropertyChanged();
OnPropertyChanged("Sum");
}
}
// Represent an Observable
private int secondNumber;
public int SecondNumber
{
get { return secondNumber; }
set
{
if (value == secondNumber)
return;
this.secondNumber = value;
OnPropertyChanged();
OnPropertyChanged("Sum");
}
}
// Represent Computed
public int Sum { get { return FirstNumber + SecondNumber; } }
}
使用C#6.0,我们可以简化OnPropertyChanged
方法的实现
public class DataCS6 : INotifyPropertyChanged
{
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
// C# 6.0
protected void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
#endregion
// Represent an Observable
private int firstNumber;
public int FirstNumber
{
get { return firstNumber; }
set
{
if (value == firstNumber)
return;
this.firstNumber = value;
OnPropertyChanged();
OnPropertyChanged("Sum");
}
}
// Represent an Observable
private int secondNumber;
public int SecondNumber
{
get { return secondNumber; }
set
{
if (value == secondNumber)
return;
this.secondNumber = value;
OnPropertyChanged();
OnPropertyChanged("Sum");
}
}
// Represent Computed
public int Sum => FirstNumber + SecondNumber;
}
更新对以下评论作出答复: 有趣!但在这里,您必须自己管理您的依赖关系。您必须触发为Sum更改的属性。在击倒中,它自己计算出哪些属性将触发在计算机上更改的属性。有办法吗 我想你可以有两个选择(至少)
此库的说明如下: 在编译时将INotifyPropertyChanged代码注入属性 以下是从下载库后的新代码 二,
干杯
var compute=()=>num1+num2代码>?从本质上讲,只有一种内置类型/接口可以确定这种ioc的方向,如observableCollection、INotifyPropertyChanged等。。。但据我所知,没有什么是这样的。但这听起来像是AOP模式(Postsharp、NConcern、Fody、Castle等)的一种特殊情况,很有趣!但在这里,您必须自己管理您的依赖关系。您必须触发为Sum更改的属性。在击倒中,它自己计算出哪些属性将触发在计算机上更改的属性。有什么办法吗?你是对的。你必须以这种方式管理你自己。事实上,我没有其他方法可以自动完成,但也许我会serach@EtienneT我根据你的评论更新了我的答案。