diff --git a/Orm/Xtensive.Orm.Oracle/Sql.Drivers.Oracle/v09/Translator.cs b/Orm/Xtensive.Orm.Oracle/Sql.Drivers.Oracle/v09/Translator.cs index 27cdccc3a..a686550a5 100644 --- a/Orm/Xtensive.Orm.Oracle/Sql.Drivers.Oracle/v09/Translator.cs +++ b/Orm/Xtensive.Orm.Oracle/Sql.Drivers.Oracle/v09/Translator.cs @@ -18,9 +18,6 @@ namespace Xtensive.Sql.Drivers.Oracle.v09 { internal class Translator : SqlTranslator { - /// - public override string NewLine => "\n"; - /// public override string BatchBegin => "BEGIN\n"; @@ -441,4 +438,4 @@ public Translator(SqlDriver driver) { } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Collections/TypeRegistrationProcessorBase.cs b/Orm/Xtensive.Orm/Collections/TypeRegistrationProcessorBase.cs index 5511e482b..88d37511a 100644 --- a/Orm/Xtensive.Orm/Collections/TypeRegistrationProcessorBase.cs +++ b/Orm/Xtensive.Orm/Collections/TypeRegistrationProcessorBase.cs @@ -65,7 +65,7 @@ protected virtual bool IsAcceptable(in TypeRegistration registration, Type type) return type.IsSubclassOf(BaseType) && (ns.IsNullOrEmpty() || (type.FullName.IndexOf(ns + ".", StringComparison.InvariantCulture) >= 0)); } - private static IList FindTypes(Assembly assembly, Type baseType, TypeFilter filter) + private static IReadOnlyList FindTypes(Assembly assembly, Type baseType, TypeFilter filter) { ArgumentNullException.ThrowIfNull(assembly); ArgumentNullException.ThrowIfNull(baseType); diff --git a/Orm/Xtensive.Orm/Collections/TypeRegistry.cs b/Orm/Xtensive.Orm/Collections/TypeRegistry.cs index b5233f73e..87a1b11dc 100644 --- a/Orm/Xtensive.Orm/Collections/TypeRegistry.cs +++ b/Orm/Xtensive.Orm/Collections/TypeRegistry.cs @@ -4,13 +4,10 @@ // Created by: Dmitri Maximov // Created: 2007.08.03 -using System; using System.Collections; using System.Collections.Frozen; -using System.Collections.Generic; using System.Diagnostics; using System.Reflection; -using System.Linq; using Xtensive.Core; using Xtensive.IoC; @@ -28,7 +25,7 @@ public class TypeRegistry : LockableBase, private readonly List types = new List(); [DebuggerBrowsable(DebuggerBrowsableState.Never)] private ISet typeSet = new HashSet(); - private readonly List actions = new List(); + private List actions = new List(); [DebuggerBrowsable(DebuggerBrowsableState.Never)] private readonly HashSet actionSet = new HashSet(); private readonly ITypeRegistrationProcessor processor; @@ -110,9 +107,8 @@ public void Register(Assembly assembly, string @namespace) public bool Register(in TypeRegistration action) { EnsureNotLocked(); - if (actionSet.Contains(action)) + if (!actionSet.Add(action)) return false; - actionSet.Add(action); actions.Add(action); return true; } @@ -126,8 +122,8 @@ private void ProcessPendingActions() isProcessingPendingActions = true; try { while (true) { - var oldActions = actions.ToList(); - actions.Clear(); + var oldActions = actions; + actions = new(); foreach (var action in oldActions) processor.Process(this, action); if (actions.Count == 0) diff --git a/Orm/Xtensive.Orm/Conversion/ConvertingEnumerable.cs b/Orm/Xtensive.Orm/Conversion/ConvertingEnumerable.cs deleted file mode 100644 index 327153132..000000000 --- a/Orm/Xtensive.Orm/Conversion/ConvertingEnumerable.cs +++ /dev/null @@ -1,60 +0,0 @@ -// Copyright (C) 2003-2010 Xtensive LLC. -// All rights reserved. -// For conditions of distribution and use, see license. -// Created by: Alex Ilyin -// Created: 2007.06.04 - -using System; -using System.Collections; -using System.Collections.Generic; -using Xtensive.Core; - - -namespace Xtensive.Conversion -{ - /// - /// An implementor performing - /// conversion from to - /// on the fly. - /// - /// The item type to convert from. - /// The item type to convert to. - public class ConvertingEnumerable : IEnumerable - { - IEnumerable innerEnumerable; - Converter converter; - - /// - public IEnumerator GetEnumerator() - { - return new ConvertingEnumerator( - innerEnumerable.GetEnumerator(), - converter); - } - - /// - IEnumerator IEnumerable.GetEnumerator() - { - return new ConvertingEnumerator( - innerEnumerable.GetEnumerator(), - converter); - } - - - // Constructors - - /// - /// Initializes a new instance of this type. - /// - /// Enumerable to wrap. - /// Item converter to use. - public ConvertingEnumerable(IEnumerable innerEnumerable, Converter converter) - { - ArgumentNullException.ThrowIfNull(innerEnumerable); - ArgumentNullException.ThrowIfNull(converter); - this.innerEnumerable = innerEnumerable; - this.converter = converter; - } - } - -} \ No newline at end of file diff --git a/Orm/Xtensive.Orm/Conversion/Internals/ConvertingEnumerator.cs b/Orm/Xtensive.Orm/Conversion/Internals/ConvertingEnumerator.cs deleted file mode 100644 index a47c8dbc6..000000000 --- a/Orm/Xtensive.Orm/Conversion/Internals/ConvertingEnumerator.cs +++ /dev/null @@ -1,84 +0,0 @@ -// Copyright (C) 2003-2010 Xtensive LLC. -// All rights reserved. -// For conditions of distribution and use, see license. -// Created by: Alex Ilyin -// Created: 2007.06.04 - -using System; -using System.Collections.Generic; -using Xtensive.Core; - - -namespace Xtensive.Conversion -{ - [Serializable] - internal sealed class ConvertingEnumerator : IEnumerator - { - private IEnumerator innerEnumerator; - private readonly Converter converter; - private T2 current; - private bool currentIsValid = false; - - internal T1 InnerCurrent - { - get { return innerEnumerator.Current; } - } - - object System.Collections.IEnumerator.Current - { - get { return Current; } - } - - public T2 Current - { - get { - if (!currentIsValid) { - current = converter(innerEnumerator.Current); - currentIsValid = true; - } - return current; - } - } - - public bool MoveNext() - { - currentIsValid = false; - return innerEnumerator.MoveNext(); - } - - public void Reset() - { - currentIsValid = false; - innerEnumerator.Reset(); - } - - - // Constructors - - /// - /// Initializes new instance of this type. - /// - /// The inner enumerator. - /// The converter. - public ConvertingEnumerator(IEnumerator innerEnumerator, Converter converter) - { - ArgumentNullException.ThrowIfNull(innerEnumerator); - ArgumentNullException.ThrowIfNull(converter); - this.innerEnumerator = innerEnumerator; - this.converter = converter; - } - - - // Destructor - - /// - /// Releases resources associated with this instance. - /// - public void Dispose() - { - currentIsValid = false; - innerEnumerator.Dispose(); - innerEnumerator = null; - } - } -} \ No newline at end of file diff --git a/Orm/Xtensive.Orm/Core/LockableBase.cs b/Orm/Xtensive.Orm/Core/LockableBase.cs index 48cb59a6d..628aec58a 100644 --- a/Orm/Xtensive.Orm/Core/LockableBase.cs +++ b/Orm/Xtensive.Orm/Core/LockableBase.cs @@ -4,50 +4,37 @@ // Created by: Alex Yakunin // Created: 2007.11.22 -using System; using System.Diagnostics; +using System.Runtime.CompilerServices; +namespace Xtensive.Core; -namespace Xtensive.Core +/// +/// Base class for implementors. +/// +[Serializable] +public abstract class LockableBase(bool isLocked = false) : ILockable { + /// + public bool IsLocked { [DebuggerStepThrough] get; private set; } = isLocked; + + [MethodImpl(MethodImplOptions.NoInlining)] + private static void ThrowInstanceIsLockedException() => throw new InstanceIsLockedException(Strings.ExInstanceIsLocked); + /// - /// Base class for implementors. + /// Ensures the object is not locked (see ) yet. /// - [Serializable] - public abstract class LockableBase: ILockable + /// The instance is locked. + public void EnsureNotLocked() { - - /// - public bool IsLocked { [DebuggerStepThrough] get; private set; } - - /// - /// Ensures the object is not locked (see ) yet. - /// - /// The instance is locked. - public void EnsureNotLocked() - { - if (IsLocked) { - throw new InstanceIsLockedException(Strings.ExInstanceIsLocked); - } + if (IsLocked) { + ThrowInstanceIsLockedException(); } + } - /// - public void Lock() => Lock(true); - - /// - public virtual void Lock(bool recursive) => IsLocked = true; - - - - // Constructors + /// + public void Lock() => Lock(true); - /// - /// Initializes new instance of this type. - /// - /// Initial property value. - protected LockableBase(bool isLocked = false) - { - IsLocked = isLocked; - } - } + /// + public virtual void Lock(bool recursive) => IsLocked = true; } diff --git a/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.ClassTable.cs b/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.ClassTable.cs index f31cdc578..e9dccce41 100644 --- a/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.ClassTable.cs +++ b/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.ClassTable.cs @@ -97,7 +97,7 @@ private void BuildClassTableIndexes(TypeInfo type) if (untypedIndexes.Contains(primaryIndex) && primaryIndex.ReflectedType == root) { primaryIndex = type.Indexes.Single(i => i.DeclaringIndex == primaryIndex.DeclaringIndex && i.IsTyped); } - var filterByTypes = type.AllDescendants.Append(type).ToList(); + var filterByTypes = type.AllDescendants.Append(type).ToArray(); // Build virtual primary index if (ancestors.Count > 0) { diff --git a/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.cs b/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.cs index f2b9b3e7a..bde8c542c 100644 --- a/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Building/Builders/IndexBuilder.cs @@ -632,7 +632,7 @@ private IndexInfo BuildJoinIndex(TypeInfo reflectedType, IEnumerable valueColumnMapping.Add((item.i, item.columns)); } - result.ValueColumnsMap = valueColumnMapping; + result.ValueColumnsMap = valueColumnMapping.ToArray(); result.ValueColumns.AddRange(GatherValueColumns(columnsToAdd)); result.Name = nameBuilder.BuildIndexName(reflectedType, result); result.Group = BuildColumnGroup(result); @@ -757,7 +757,7 @@ private IndexInfo BuildViewIndex(TypeInfo reflectedType, IndexInfo indexToApplyV } result.ValueColumns.AddRange(valueColumns); - result.SelectColumns = columnMap; + result.SelectColumns = columnMap.ToArray(); result.Name = nameBuilder.BuildIndexName(reflectedType, result); result.Group = BuildColumnGroup(result); diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs index 8b28a6f50..fa693980c 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs @@ -26,7 +26,7 @@ internal sealed class StructureExpression : ParameterizedExpression, IPersistent public IReadOnlyList Fields => fields; - private void SetFields(List value) + private void SetFields(IReadOnlyList value) { fields = value; foreach (var fieldExpression in fields.OfType()) { @@ -42,10 +42,11 @@ public override Expression Remap(ColNum offset, Dictionary((ColNum) (Mapping.Offset + offset), Mapping.Length); var result = new StructureExpression(PersistentType, mapping); processedExpressions.Add(this, result); - var processedFields = new List(fields.Count); + var processedFields = new PersistentFieldExpression[fields.Count]; + int i = 0; foreach (var field in fields) { // Do not convert to LINQ. We intentionally avoiding closure creation here - processedFields.Add(field.Remap(offset, processedExpressions)); + processedFields[i++] = field.Remap(offset, processedExpressions); } result.SetFields(processedFields); @@ -96,10 +97,11 @@ public override ParameterizedExpression BindParameter(ParameterExpression parame var result = new StructureExpression(PersistentType, Mapping); processedExpressions.Add(this, result); - var processedFields = new List(fields.Count); + var processedFields = new PersistentFieldExpression[fields.Count]; + int i = 0; foreach (var field in fields) { // Do not convert to LINQ. We intentionally avoiding closure creation here - processedFields.Add((PersistentFieldExpression) field.BindParameter(parameter, processedExpressions)); + processedFields[i++] = (PersistentFieldExpression) field.BindParameter(parameter, processedExpressions); } result.SetFields(processedFields); @@ -114,10 +116,11 @@ public override Expression RemoveOuterParameter(Dictionary(fields.Count); + var processedFields = new PersistentFieldExpression[fields.Count]; + int i = 0; foreach (var field in fields) { // Do not convert to LINQ. We intentionally avoiding closure creation here - processedFields.Add((PersistentFieldExpression) field.RemoveOuterParameter(processedExpressions)); + processedFields[i++] = (PersistentFieldExpression) field.RemoveOuterParameter(processedExpressions); } result.SetFields(processedFields); @@ -131,12 +134,13 @@ public static StructureExpression CreateLocalCollectionStructure(TypeInfo typeIn } var sourceFields = typeInfo.Fields; - var destinationFields = new List(sourceFields.Count); + var destinationFields = new PersistentFieldExpression[sourceFields.Count]; var result = new StructureExpression(typeInfo, mapping); result.SetFields(destinationFields); + int i = 0; foreach (var field in sourceFields) { // Do not convert to LINQ. We intentionally avoiding closure creation here - destinationFields.Add(BuildNestedFieldExpression(field, mapping.Offset)); + destinationFields[i++] = BuildNestedFieldExpression(field, mapping.Offset); } return result; diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs index c5f0175cb..d5142c056 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs @@ -37,10 +37,11 @@ public override StructureFieldExpression Remap(ColNum offset, Dictionary((ColNum) (Mapping.Offset + offset), Mapping.Length); var result = new StructureFieldExpression(PersistentType, Field, newMapping, OuterParameter, DefaultIfEmpty); processedExpressions.Add(this, result); - var processedFields = new List(fields.Count); + var processedFields = new PersistentFieldExpression[fields.Count]; + int i = 0; foreach (var field in fields) { // Do not convert to LINQ. We want to avoid a closure creation here. - processedFields.Add(field.Remap(offset, processedExpressions)); + processedFields[i++] = field.Remap(offset, processedExpressions); } if (Owner == null) { @@ -163,10 +164,11 @@ public static StructureFieldExpression CreateStructure(FieldInfo structureField, var fieldMappingInfo = structureField.MappingInfo; var mapping = new Segment((ColNum)(offset + fieldMappingInfo.Offset), fieldMappingInfo.Length); var result = new StructureFieldExpression(persistentType, structureField, mapping, null, false); - var processedFields = new List(persistentType.Fields.Count); + var processedFields = new PersistentFieldExpression[persistentType.Fields.Count]; + int i = 0; foreach (var field in persistentType.Fields) { // Do not convert to LINQ. We want to avoid a closure creation here. - processedFields.Add(BuildNestedFieldExpression(field, (ColNum) (offset + fieldMappingInfo.Offset))); + processedFields[i++] = BuildNestedFieldExpression(field, (ColNum) (offset + fieldMappingInfo.Offset)); } result.SetFields(processedFields); diff --git a/Orm/Xtensive.Orm/Orm/Model/IndexInfo.cs b/Orm/Xtensive.Orm/Orm/Model/IndexInfo.cs index a1d29c917..f298cdf0a 100644 --- a/Orm/Xtensive.Orm/Orm/Model/IndexInfo.cs +++ b/Orm/Xtensive.Orm/Orm/Model/IndexInfo.cs @@ -4,11 +4,7 @@ // Created by: Alex Ustinov // Created: 2007.07.10 -using System; -using System.Collections.Generic; -using System.Collections.ObjectModel; using System.Diagnostics; -using System.Linq; using System.Linq.Expressions; using Xtensive.Collections; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Sql/Compiler/SqlTranslator.cs b/Orm/Xtensive.Orm/Sql/Compiler/SqlTranslator.cs index 3282fc67a..a6ed0ff56 100644 --- a/Orm/Xtensive.Orm/Sql/Compiler/SqlTranslator.cs +++ b/Orm/Xtensive.Orm/Sql/Compiler/SqlTranslator.cs @@ -34,7 +34,7 @@ public abstract class SqlTranslator : SqlDriverBound public NumberFormatInfo FloatNumberFormat { get; private set; } public NumberFormatInfo DoubleNumberFormat { get; private set; } - public virtual string NewLine { get { return Environment.NewLine; } } + public string NewLine { get; } = "\n"; public virtual string OpeningParenthesis => "("; public virtual string ClosingParenthesis => ")"; @@ -2491,26 +2491,23 @@ public virtual string BuildBatch(IReadOnlyList statements) } var expectedLength = BatchBegin.Length + BatchEnd.Length + ((BatchItemDelimiter.Length + NewLine.Length) * statements.Count) - + statements.Sum(statement => statement.Length); - var valueBuilder = new ValueStringBuilder(expectedLength); - valueBuilder.Append(BatchBegin); + + statements.Sum(static statement => statement.Length); + StringBuilder sb = new(BatchBegin, expectedLength); foreach (var statement in statements) { - var statementAsSpan = (ReadOnlySpan) statement; - var actualStatement = statementAsSpan + var actualStatement = statement.AsSpan() .Trim() .TryCutPrefix(BatchBegin) .TryCutSuffix(BatchEnd) .TryCutSuffix(NewLine) .TryCutSuffix(BatchItemDelimiter) .Trim(); - if (actualStatement.Length == 0) - continue; - valueBuilder.Append(actualStatement.ToString()); - valueBuilder.Append(BatchItemDelimiter); - valueBuilder.Append(NewLine); - } - valueBuilder.Append(BatchEnd); - return valueBuilder.ToString(); + if (actualStatement.Length != 0) { + _ = sb.Append(actualStatement) + .Append(BatchItemDelimiter) + .Append(NewLine); + } + } + return sb.Append(BatchEnd).ToString(); } /// diff --git a/Orm/Xtensive.Orm/Sql/SqlHelper.cs b/Orm/Xtensive.Orm/Sql/SqlHelper.cs index f25670f2c..c24da3488 100644 --- a/Orm/Xtensive.Orm/Sql/SqlHelper.cs +++ b/Orm/Xtensive.Orm/Sql/SqlHelper.cs @@ -564,8 +564,9 @@ public static NotSupportedException NotSupported(ServerFeatures feature) public static void NotifyConnectionOpening( IEnumerable connectionAccessors, DbConnection connection, bool reconnect = false) { + ConnectionEventData eventData = null; foreach (var accessor in connectionAccessors) { - accessor.ConnectionOpening(new ConnectionEventData(connection, reconnect)); + accessor.ConnectionOpening(eventData ??= new ConnectionEventData(connection, reconnect)); } } @@ -582,9 +583,10 @@ public static void NotifyConnectionOpening( public static async Task NotifyConnectionOpeningAsync( IEnumerable connectionAccessors, DbConnection connection, bool reconnect = false, CancellationToken token = default) { + ConnectionEventData eventData = null; foreach (var accessor in connectionAccessors) { await accessor.ConnectionOpeningAsync( - new ConnectionEventData(connection, reconnect), token) + eventData ??= new ConnectionEventData(connection, reconnect), token) .ConfigureAwaitFalse(); } }