asp.net 4.5中有一个新的应用程序设置
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true" />
Run Code Online (Sandbox Code Playgroud)
像这样的代码可以在asp.net 4.0中运行
protected void Button1_Click(object sender, EventArgs e)
{
CallAysnc();
}
public void CallAysnc()
{
AsyncOperation asyncOp = AsyncOperationManager.CreateOperation(Guid.NewGuid().ToString());
WebClient client = new WebClient();
client.DownloadStringCompleted += (object sender, DownloadStringCompletedEventArgs e) =>
{
asyncOp.PostOperationCompleted(CallCompleted, e.Result);
};
client.DownloadStringAsync(new Uri("http://www.google.com"));
}
private void CallCompleted(object args)
{
Response.Write(args.ToString());
}
Run Code Online (Sandbox Code Playgroud)
但它在asp.net 4.5中不起作用,当我删除新的appsetting时,它再次起作用!
那么"UseTaskFriendlySynchronizationContext"的含义是什么?
对于基本身份验证,我已经实现了一个HttpMessageHandler基于Darin Dimitrov在这里回答的示例的自定义:https://stackoverflow.com/a/11536349/270591
代码创建具有用户名和角色principal的类型实例,GenericPrincipal然后将此主体设置为线程的当前主体:
Thread.CurrentPrincipal = principal;
Run Code Online (Sandbox Code Playgroud)
稍后在ApiController方法中,可以通过访问controllers User属性来读取主体:
public class ValuesController : ApiController
{
public void Post(TestModel model)
{
var user = User; // this should be the principal set in the handler
//...
}
}
Run Code Online (Sandbox Code Playgroud)
这似乎工作正常,直到我最近添加了一个MediaTypeFormatter使用该Task库的自定义,如下所示:
public override Task<object> ReadFromStreamAsync(Type type, Stream readStream,
HttpContent content, IFormatterLogger formatterLogger)
{
var task = Task.Factory.StartNew(() =>
{
// some formatting happens and finally a TestModel is …Run Code Online (Sandbox Code Playgroud) 我正在使用Dispatcher这样从外部切换到UI线程
Application.Current.Dispatcher.Invoke(myAction);
Run Code Online (Sandbox Code Playgroud)
但我在一些论坛上看到人们建议使用Synchronization上下文而不是Dispatcher.
SynchronizationContext.Current.Post(myAction,null);
Run Code Online (Sandbox Code Playgroud)
它们之间有什么区别,为什么SynchronizationContext要使用它?
在Unity中,说您有一个GameObject。因此,可能是劳拉·克罗夫特(Lara Croft),马里奥(Mario),愤怒的鸟,特定的立方体,特定的树或其他任何东西。
(回想一下,Unity不是OO,它是ECS。Component可以“附加”到s的s本身可以GameObject用OO语言创建,也可以不使用OO语言创建,但是Unity本身只是GameObjects 的列表和运行任何Components 的框架引擎。因此,实际上Unity当然是“完全”的单线程,甚至没有一种概念上的方法可以在另外1个线程上执行与“实际Unity”(“游戏对象列表”)相关的任何操作。)
所以说在多维数据集上,我们有一个Component称为Test
public class Test: MonoBehaviour {
Run Code Online (Sandbox Code Playgroud)
它确实具有Update伪函数,因此Unity知道我们要在每个帧中运行一些东西。
private void Update() { // this is Test's Update call
Debug.Log(ManagedThreadId); // definitely 101
if (something) DoSomethingThisParticularFrame();
}
Run Code Online (Sandbox Code Playgroud)
假设统一线程为“ 101”。
这样更新(实际上是任何游戏对象上任何框架的任何更新)都将打印101。
因此,由于某种原因,我们有时会选择每隔几秒钟运行一次DoSomethingThisFrame。
因此,每一帧(显然,在“该” Unity线程上……有/只能有一个线程),Unity在各种游戏对象上运行所有Update调用。
因此,在一个特定的帧(比如说游戏的第819秒的第24帧)上,它确实DoSomethingThisParticularFrame为我们运行。
void DoSomethingThisParticularFrame() {
Debug.Log(ManagedThreadId); // 101 I think
TrickyBusiness();
}
Run Code Online (Sandbox Code Playgroud)
我认为这也会打印101。
async void TrickyBusiness() {
Debug.Log("A.. " + ManagedThreadId); // 101 I think
var aTask …Run Code Online (Sandbox Code Playgroud) 假设我有一个简单的C#控制台应用程序:
class Program
{
static async void func()
{
Thread.CurrentThread.Name = "main";
await Task.Run(() =>
{
Thread.CurrentThread.Name = "child";
Thread.Sleep(5000);
});
Console.WriteLine("continuation is running on {0} thread", Thread.CurrentThread.Name);
}
static void Main(string[] args)
{
func();
Thread.Sleep(10000);
}
}
Run Code Online (Sandbox Code Playgroud)
当5000毫秒通过时,我们看到"继续在子线程上运行"消息.当另一个5000毫秒通过时,主线程完成其工作并关闭应用程序.它看起来很合乎逻辑:异步任务及其延续在同一子线程上运行.
但现在假设我有一个简单的WPF应用程序:
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
async private void mainWnd_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
Thread.CurrentThread.Name = "main";
await Task.Run(() =>
{
Thread.CurrentThread.Name = "child";
Thread.Sleep(5000);
});
this.Title = string.Format("continuation is …Run Code Online (Sandbox Code Playgroud) .net ×3
c# ×3
asp.net ×2
asynchronous ×2
asp.net-mvc ×1
async-await ×1
security ×1
task ×1
wpf ×1