我在.Net中遇到了一些关于垃圾收集的奇怪行为.
以下程序将非常快速地抛出OutOfMemoryException(在32位,2GB机器上不到一秒钟之后).永远不会调用Foo终结器.
class Foo
{
Guid guid = Guid.NewGuid();
byte[] buffer = new byte[1000000];
static Random rand = new Random();
public Foo()
{
// Uncomment the following line and the program will run forever.
// rand.NextBytes(buffer);
}
~Foo()
{
// This finalizer is never called unless the rand.NextBytes
// line in the constructor is uncommented.
}
static public void Main(string args[])
{
for (; ; )
{
new Foo();
}
}
}
Run Code Online (Sandbox Code Playgroud)
如果取消注释rand.nextBytes行,它将无限运行,并定期调用Foo终结器.这是为什么?
我最好的猜测是,在前一种情况下,CLR或Windows VMM都懒得分配物理内存.永远不会写入缓冲区,因此永远不会使用物理内存.当地址空间用完时,系统崩溃.在后一种情况下,系统在用完地址空间之前耗尽物理内存,触发GC并收集对象.
但是,这是我没有得到的部分.假设我的理论是正确的,为什么地址空间不足时GC不会触发?如果我的理论不正确,那么真正的解释是什么呢?
我正在研究一个需要高文件I/O性能的系统(使用C#).基本上,我从文件的开头填充大文件(~100MB)直到文件结束.每隔约5秒我就会向文件中添加〜5MB(从文件的开头顺序),每次批量我都在刷新流.每隔几分钟我就需要更新一个我在文件末尾写的结构(某种元数据).
当冲洗每个散装时,我没有性能问题.但是,当更新文件末尾的元数据时,我的性能确实很低.我的猜测是,在创建文件时(也应该加快速度),文件并不真正在磁盘上分配整个100MB,当我刷新元数据时,它必须分配所有空间直到文件结束.
男孩/女孩,任何想法我怎么能克服这个问题?
非常感谢!
来自评论:
一般来说,代码如下,首先打开文件:
m_Stream = new FileStream(filename,
FileMode.CreateNew,
FileAccess.Write,
FileShare.Write, 8192, false);
m_Stream.SetLength(100*1024*1024);
Run Code Online (Sandbox Code Playgroud)
每隔几秒我就会写5MB.
m_Stream.Seek(m_LastPosition, SeekOrigin.Begin);
m_Stream.Write(buffer, 0, buffer.Length);
m_Stream.Flush();
m_LastPosition += buffer.Length; // HH: guessed the +=
m_Stream.Seek(m_MetaDataSize, SeekOrigin.End);
m_Stream.Write(metadata, 0, metadata.Length);
m_Stream.Flush(); // Takes too long on the first time(~1 sec).
Run Code Online (Sandbox Code Playgroud) 有关于每个枚举的定义的文档.但是我怎么能在实践中演示/看到这个?我怎么可能知道何时使用哪个优先级?
下面是一些代码,我已经在尝试看到先决如何影响排序创建的,它为我提供了证据,证明的顺序是正确的(第一循环迭代将增加一个SystemIdle枚举到调度队列),但它仍然有加最后一个字符串
private void btn_Click(object sender, RoutedEventArgs e)
{
StringBuilder result = new StringBuilder();
new Thread(() =>
{
var vals = Enum.GetValues(typeof(DispatcherPriority)).Cast<DispatcherPriority>().Where(y => y >= 0).ToList();
vals.Reverse();
vals.ForEach(x =>
{
Dispatcher.BeginInvoke(new Action(() =>
{
result.AppendLine(string.Format("Priority: {0} Enum:{1}", ((int)x), x.ToString()));
}), x);
});
}).Start();
ShowResultAsync(result, 2000);
}
private async void ShowResultAsync(StringBuilder s, int delay)
{
await Task.Delay(delay);
MessageBox.Show(s.ToString());
}
Run Code Online (Sandbox Code Playgroud)
并且输出顺序保持不变,即使列表反转(在vals分配后添加此行):
vals.Reverse();
Run Code Online (Sandbox Code Playgroud)
那么,在确定我应该分配哪个调度优先级时,还有什么我可以使用的吗?
HttpClient默认包含"Keep-Alive".我已经能够将其设置为"关闭",httpClient.DefaultRequestHeaders.ConnectionClose = true;但如何完全省略它?
使用此构造:
var dict = new Dictionary<int, string>();
var result = (dict?.TryGetValue(1, out var value) ?? false) ? value : "Default";
Run Code Online (Sandbox Code Playgroud)
我收到一个错误消息,说CS0165 use of unassigned local variable 'value'那不是我期望的。怎么value可能不确定?如果字典为null,则将返回内部语句false,这将使外部语句的值为false,返回Default。
我在这里想念什么?只是编译器无法完全评估该语句吗?还是我搞砸了?
我正在尝试将一些代码从 WPF 迁移到 Blazor。WPF 代码依赖 ShowDialog() 来显示模式对话框并暂停执行,直到模式关闭。是否有(服务器端)Blazor 等效项允许基于 C# 控制流,例如,用户是否在模式对话框中单击了确认与取消?
我在预览版 8 中创建了一个新的 Blazor 服务器端应用程序。当我调用 UriHelper.NavigateTo 从 Index.razor 页面转到计数器页面时,计数器页面被调用两次。
在 Index.razor 页面中,我有以下代码:
@code{
protected async override Task OnInitializedAsync()
{
UriHelper.NavigateTo("/counter");
}
}
Run Code Online (Sandbox Code Playgroud)
然后在计数器页面中,我添加了以下带有断点的代码:
protected override void OnInitialized()
{
}
Run Code Online (Sandbox Code Playgroud)
我的期望是当 NavigateTo 在 Index.razor 中调用计数器路由时只调用一次计数器页面
我对开发相当陌生,并尝试使用 Blazor 学习 C# 开发。我目前正在学习如何使用 构建表单EditForms并使用 进行验证DataAnnotationsValidator。
在继续处理表单之前,我已经成功完成了验证所需的大部分工作,但是,我在验证的一个重要方面遇到了麻烦:我正在处理的表单是新用户的注册表单。通常,在注册新用户时,您可能希望让用户重新输入电子邮件地址或密码等值,以确保他们输入正确:
<InputText @bind-Value=User.email id="email" /><br />
<ValidationMessage For=@( () => User.email) />
<label for="confirm">Confirm Email</label><br />
<InputText @bind-Value=User.confirm id="confirm"/><br />
Run Code Online (Sandbox Code Playgroud)
为了验证这些字段,我有类 UserModel,我已将其实例化为 User()。
@code
{
UserModel User = new UserModel();
class UserModel
{
[Required]
[EmailAddress(ErrorMessage = "Please enter a valid email address.")]
public string email { get; set; }
[Required]
[EmailAddress(ErrorMessage = "Please confirm your email address.")]
[Compare(email, ErrorMessage = "The email addresses you entered did not match.")]
public …Run Code Online (Sandbox Code Playgroud) c# ×8
blazor ×3
.net ×1
asp.net-core ×1
clr ×1
dispatcher ×1
file-io ×1
http-headers ×1
out ×1
performance ×1
regex ×1
winforms ×1
wpf ×1