From 182f1aef06140e95191f3ad12a30e9cad446c028 Mon Sep 17 00:00:00 2001 From: test Date: Tue, 5 Feb 2019 20:54:24 +0900 Subject: [PATCH] =?utf8?q?=E3=82=BB=E3=83=9E=E3=83=95=E3=82=A9=E3=83=BC?= =?utf8?q?=E3=81=A0=E3=81=A8=E3=83=87=E3=83=83=E3=83=89=E3=83=AD=E3=83=83?= =?utf8?q?=E3=82=AF=E3=82=92=E8=B5=B7=E3=81=93=E3=81=99=E3=81=93=E3=81=A8?= =?utf8?q?=E3=81=8C=E3=81=82=E3=82=8B=E3=81=AE=E3=81=A7=E3=83=AA=E3=83=BC?= =?utf8?q?=E3=83=80=E3=83=BC=E3=83=A9=E3=82=A4=E3=82=BF=E3=83=BC=E3=83=AD?= =?utf8?q?=E3=83=83=E3=82=AB=E3=83=BC=E3=81=AB=E5=A4=89=E6=9B=B4=E3=81=97?= =?utf8?q?=E3=81=9F?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit --- Core/Document.cs | 23 ++------------ Core/StringBuffer.cs | 84 ++++++++++++++++++++++++++++------------------------ 2 files changed, 47 insertions(+), 60 deletions(-) diff --git a/Core/Document.cs b/Core/Document.cs index 0a42405..ed6fdf3 100644 --- a/Core/Document.cs +++ b/Core/Document.cs @@ -1160,30 +1160,11 @@ namespace FooEditEngine { try { - await this.buffer.LockAsync().ConfigureAwait(false); - StringBuilder line = new StringBuilder(); - for (int i = 0; i < this.Length; i++) - { - char c = this[i]; - line.Append(c); - if (c == Document.NewLine || i == this.Length - 1) - { - string str = line.ToString(); - str = str.Replace(Document.NewLine.ToString(), fs.NewLine); - await fs.WriteAsync(str).ConfigureAwait(false); - line.Clear(); - if (tokenSource != null) - tokenSource.Token.ThrowIfCancellationRequested(); -#if TEST_ASYNC - System.Threading.Thread.Sleep(10); -#endif - } - } - this.Dirty = false; + await this.buffer.SaveAsync(fs, tokenSource); } finally { - this.buffer.UnLock(); + this.Dirty = false; } } diff --git a/Core/StringBuffer.cs b/Core/StringBuffer.cs index 0fdc448..57aaacd 100644 --- a/Core/StringBuffer.cs +++ b/Core/StringBuffer.cs @@ -41,6 +41,7 @@ namespace FooEditEngine GapBuffer buf = new GapBuffer(); const int MaxSemaphoreCount = 1; SemaphoreSlim Semaphore = new SemaphoreSlim(MaxSemaphoreCount); + ReaderWriterLockSlim rwlock = new ReaderWriterLockSlim(); public StringBuffer() { @@ -58,31 +59,6 @@ namespace FooEditEngine } } - /// - /// ロックを解除します - /// - public void UnLock() - { - this.Semaphore.Release(); - } - - /// - /// ロックします - /// - public void Lock() - { - this.Semaphore.Wait(); - } - - /// - /// ロックします - /// - /// Taskオブジェクト - public Task LockAsync() - { - return this.Semaphore.WaitAsync(); - } - public StringBuffer(StringBuffer buffer) : this() { @@ -101,14 +77,14 @@ namespace FooEditEngine public string ToString(int index, int length) { - this.Lock(); + this.rwlock.EnterReadLock(); StringBuilder temp = new StringBuilder(); temp.Clear(); for (int i = index; i < index + length; i++) temp.Append(buf[i]); - this.UnLock(); + this.rwlock.ExitReadLock(); return temp.ToString(); } @@ -170,19 +146,19 @@ namespace FooEditEngine internal void Replace(GapBuffer buf) { - this.Lock(); + this.rwlock.EnterWriteLock(); this.Clear(); this.buf = buf; - this.UnLock(); + this.rwlock.ExitWriteLock(); this.Update(this, new DocumentUpdateEventArgs(UpdateType.Replace, 0, 0, buf.Count)); } internal void Replace(int index, int length, IEnumerable chars,int count) { - this.Lock(); + this.rwlock.EnterWriteLock(); try{ if (length > 0) @@ -191,7 +167,7 @@ namespace FooEditEngine } finally { - this.UnLock(); + this.rwlock.ExitWriteLock(); } this.Update(this, new DocumentUpdateEventArgs(UpdateType.Replace, index, length, count)); @@ -212,11 +188,11 @@ namespace FooEditEngine //内部形式に変換する var internal_str = from s in str where s != '\r' && s != '\0' select s; - await this.LockAsync().ConfigureAwait(false); + this.rwlock.EnterWriteLock(); //str.lengthは事前に確保しておくために使用するので影響はない this.buf.InsertRange(index, internal_str, str.Length); - this.UnLock(); + this.rwlock.ExitWriteLock(); if (tokenSource != null) tokenSource.Token.ThrowIfCancellationRequested(); @@ -228,6 +204,36 @@ namespace FooEditEngine } while (readCount > 0); } + internal async Task SaveAsync(TextWriter fs,CancellationTokenSource tokenSource=null) + { + try + { + this.rwlock.EnterWriteLock(); + StringBuilder line = new StringBuilder(); + for (int i = 0; i < this.Length; i++) + { + char c = this[i]; + line.Append(c); + if (c == Document.NewLine || i == this.Length - 1) + { + string str = line.ToString(); + str = str.Replace(Document.NewLine.ToString(), fs.NewLine); + await fs.WriteAsync(str).ConfigureAwait(false); + line.Clear(); + if (tokenSource != null) + tokenSource.Token.ThrowIfCancellationRequested(); +#if TEST_ASYNC + System.Threading.Thread.Sleep(10); +#endif + } + } + } + finally + { + this.rwlock.ExitWriteLock(); + } + } + internal void ReplaceRegexAll(LineToIndexTable layoutlines, Regex regex, string pattern, bool groupReplace) { for (int i = 0; i < layoutlines.Count; i++) @@ -241,7 +247,7 @@ namespace FooEditEngine return pattern; }); - this.Lock(); + this.rwlock.EnterWriteLock(); try { //空行は削除する必要はない @@ -251,7 +257,7 @@ namespace FooEditEngine } finally { - this.UnLock(); + this.rwlock.ExitWriteLock(); } this.Update(this, new DocumentUpdateEventArgs(UpdateType.Replace, lineHeadIndex, lineLength, output.Length, i)); @@ -269,7 +275,7 @@ namespace FooEditEngine int newLineLength = lineLength; while ((right = ts.IndexOf(this.buf, left, lineHeadIndex + newLineLength)) != -1) { - this.Lock(); + this.rwlock.EnterWriteLock(); try { this.buf.RemoveRange(right, target.Length); @@ -277,7 +283,7 @@ namespace FooEditEngine } finally { - this.UnLock(); + this.rwlock.ExitWriteLock(); } left = right + pattern.Length; @@ -291,12 +297,12 @@ namespace FooEditEngine internal int IndexOf(string target, int start,bool ci = false) { - this.Lock(); + this.rwlock.EnterReadLock(); TextSearch ts = new TextSearch(target,ci); int patternIndex = ts.IndexOf(this.buf, start,this.buf.Count); - this.UnLock(); + this.rwlock.ExitReadLock(); return patternIndex; } -- 2.11.0