Enable CA1825: Avoid zero-length array allocations (#13961)

This commit is contained in:
xtqqczze 2020-11-04 03:56:26 +00:00 committed by GitHub
parent 3444595e78
commit 1d7a93c2e0
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
17 changed files with 57 additions and 54 deletions

View file

@ -286,7 +286,7 @@ dotnet_diagnostic.CA1823.severity = none
dotnet_diagnostic.CA1824.severity = suggestion
# CA1825: Avoid zero-length array allocations
dotnet_diagnostic.CA1825.severity = suggestion
dotnet_diagnostic.CA1825.severity = warning
# CA1826: Do not use Enumerable methods on indexable collections
dotnet_diagnostic.CA1826.severity = suggestion

View file

@ -111,9 +111,6 @@ Some general guidelines:
* Avoid using string interpolations and overloads with implicit parameters such as `Culture` and `StringComparison`.
Instead, use overloads with more explicit parameters such as `String.Format(IFormatProvider, String, Object[])` and `Equals(String, String, StringComparison)`.
* Avoid creating empty arrays.
Instead, reuse the static ones via `Utils.EmptyArray<T>`.
* Avoid unnecessary memory allocation in a loop.
Move the memory allocation outside the loop if possible.

View file

@ -480,7 +480,7 @@ namespace Microsoft.PowerShell.Commands
}
}
private ModuleSpecification[] _moduleSpecifications = new ModuleSpecification[0];
private ModuleSpecification[] _moduleSpecifications = Array.Empty<ModuleSpecification>();
internal bool IsFullyQualifiedModuleSpecified = false;
private bool _commandParameterSpecified; // initialized to default value in the constructor

View file

@ -366,7 +366,7 @@ namespace Microsoft.PowerShell.Commands
/// <summary>
/// Gets or sets a list of all Regex matches on the matching line.
/// </summary>
public Match[] Matches { get; set; } = new Match[] { };
public Match[] Matches { get; set; } = Array.Empty<Match>();
/// <summary>
/// Create a deep copy of this MatchInfo instance.
@ -1897,8 +1897,8 @@ namespace Microsoft.PowerShell.Commands
if (matchInfo.Context != null)
{
matchResult = matchInfo.Clone();
matchResult.Context.DisplayPreContext = new string[] { };
matchResult.Context.DisplayPostContext = new string[] { };
matchResult.Context.DisplayPreContext = Array.Empty<string>();
matchResult.Context.DisplayPostContext = Array.Empty<string>();
}
else
{
@ -1924,7 +1924,7 @@ namespace Microsoft.PowerShell.Commands
// Matches should be an empty list, rather than null,
// in the cases of notMatch and simpleMatch.
matchResult.Matches = matches ?? new Match[] { };
matchResult.Matches = matches ?? Array.Empty<Match>();
return true;
}

View file

@ -207,7 +207,7 @@ namespace Microsoft.PowerShell.Commands
ConstructorInfo ci = type.GetConstructor(Type.EmptyTypes);
if (ci != null && ci.IsPublic)
{
_newObject = CallConstructor(type, new ConstructorInfo[] { ci }, new object[] { });
_newObject = CallConstructor(type, new ConstructorInfo[] { ci }, Array.Empty<object>());
if (_newObject != null && Property != null)
{
// The method invocation is disabled for "Hashtable to Object conversion" (Win8:649519), but we need to keep it enabled for New-Object for compatibility to PSv2

View file

@ -599,7 +599,7 @@ namespace System.Management.Automation
if (_engineEventSubscribers.TryGetValue(PSEngineEvent.OnIdle, out subscribers) && subscribers.Count > 0)
{
// We send out on-idle event and keep enabling the timer only if there still are subscribers to the on-idle event
GenerateEvent(PSEngineEvent.OnIdle, null, new object[] { }, null, false, false);
GenerateEvent(PSEngineEvent.OnIdle, null, Array.Empty<object>(), null, false, false);
EnableTimer();
}
else

View file

@ -384,7 +384,7 @@ namespace System.Management.Automation
emitter.Emit(OpCodes.Ldarg_0);
emitter.Emit(OpCodes.Castclass, _enumerableType);
MethodInfo methodInfo = _enumerableType.GetMethod("GetEnumerator", new Type[] { });
MethodInfo methodInfo = _enumerableType.GetMethod("GetEnumerator", Array.Empty<Type>());
emitter.Emit(OpCodes.Callvirt, methodInfo);
emitter.Emit(OpCodes.Ret);
}

View file

@ -6882,7 +6882,7 @@ namespace Microsoft.PowerShell.Commands
iss.Bind(Context, updateOnly: true, module, options.NoClobber, options.Local, setLocation: false);
// Scan all of the types in the assembly to register JobSourceAdapters.
IEnumerable<Type> allTypes = new Type[] { };
IEnumerable<Type> allTypes = Array.Empty<Type>();
if (assembly != null)
{
allTypes = assembly.ExportedTypes;

View file

@ -1559,7 +1559,7 @@ namespace System.Management.Automation
toType,
0,
null,
new object[] { },
Array.Empty<object>(),
System.Globalization.CultureInfo.InvariantCulture);
if (collectionTypeInformation.ParameterCollectionType == ParameterCollectionType.IList)
resultAsIList = (IList)resultCollection;

View file

@ -236,6 +236,6 @@ namespace System.Management.Automation
/// </summary>
public object Data { get; set; }
internal static readonly RuntimeDefinedParameter[] EmptyParameterArray = new RuntimeDefinedParameter[0];
internal static readonly RuntimeDefinedParameter[] EmptyParameterArray = Array.Empty<RuntimeDefinedParameter>();
}
}

View file

@ -851,7 +851,7 @@ namespace System.Management.Automation.Runspaces
// Generate the shutdown event
if (Events != null)
Events.GenerateEvent(PSEngineEvent.Exiting, null, new object[] { }, null, true, false);
Events.GenerateEvent(PSEngineEvent.Exiting, null, Array.Empty<object>(), null, true, false);
// Stop all running pipelines
// Note:Do not perform the Cancel in lock. Reason is

View file

@ -144,35 +144,35 @@ namespace System.Management.Automation.Remoting
typeof(PSHost),
"get_Name",
typeof(string),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetVersion:
return new RemoteHostMethodInfo(
typeof(PSHost),
"get_Version",
typeof(Version),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetInstanceId:
return new RemoteHostMethodInfo(
typeof(PSHost),
"get_InstanceId",
typeof(Guid),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetCurrentCulture:
return new RemoteHostMethodInfo(
typeof(PSHost),
"get_CurrentCulture",
typeof(System.Globalization.CultureInfo),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetCurrentUICulture:
return new RemoteHostMethodInfo(
typeof(PSHost),
"get_CurrentUICulture",
typeof(System.Globalization.CultureInfo),
new Type[] { });
Array.Empty<Type>());
// Host methods.
@ -188,28 +188,28 @@ namespace System.Management.Automation.Remoting
typeof(PSHost),
"EnterNestedPrompt",
typeof(void),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.ExitNestedPrompt:
return new RemoteHostMethodInfo(
typeof(PSHost),
"ExitNestedPrompt",
typeof(void),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.NotifyBeginApplication:
return new RemoteHostMethodInfo(
typeof(PSHost),
"NotifyBeginApplication",
typeof(void),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.NotifyEndApplication:
return new RemoteHostMethodInfo(
typeof(PSHost),
"NotifyEndApplication",
typeof(void),
new Type[] { });
Array.Empty<Type>());
// Host UI methods.
@ -218,14 +218,14 @@ namespace System.Management.Automation.Remoting
typeof(PSHostUserInterface),
"ReadLine",
typeof(string),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.ReadLineAsSecureString:
return new RemoteHostMethodInfo(
typeof(PSHostUserInterface),
"ReadLineAsSecureString",
typeof(System.Security.SecureString),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.Write1:
return new RemoteHostMethodInfo(
@ -246,7 +246,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostUserInterface),
"WriteLine",
typeof(void),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.WriteLine2:
return new RemoteHostMethodInfo(
@ -339,7 +339,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_ForegroundColor",
typeof(ConsoleColor),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetForegroundColor:
return new RemoteHostMethodInfo(
@ -353,7 +353,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_BackgroundColor",
typeof(ConsoleColor),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetBackgroundColor:
return new RemoteHostMethodInfo(
@ -367,7 +367,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_CursorPosition",
typeof(Coordinates),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetCursorPosition:
return new RemoteHostMethodInfo(
@ -381,7 +381,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_WindowPosition",
typeof(Coordinates),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetWindowPosition:
return new RemoteHostMethodInfo(
@ -395,7 +395,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_CursorSize",
typeof(int),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetCursorSize:
return new RemoteHostMethodInfo(
@ -409,7 +409,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_BufferSize",
typeof(Size),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetBufferSize:
return new RemoteHostMethodInfo(
@ -423,7 +423,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_WindowSize",
typeof(Size),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetWindowSize:
return new RemoteHostMethodInfo(
@ -437,7 +437,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_WindowTitle",
typeof(string),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetWindowTitle:
return new RemoteHostMethodInfo(
@ -453,21 +453,21 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"get_MaxWindowSize",
typeof(Size),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetMaxPhysicalWindowSize:
return new RemoteHostMethodInfo(
typeof(PSHostRawUserInterface),
"get_MaxPhysicalWindowSize",
typeof(Size),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetKeyAvailable:
return new RemoteHostMethodInfo(
typeof(PSHostRawUserInterface),
"get_KeyAvailable",
typeof(bool),
new Type[] { });
Array.Empty<Type>());
// Host raw UI methods.
@ -483,7 +483,7 @@ namespace System.Management.Automation.Remoting
typeof(PSHostRawUserInterface),
"FlushInputBuffer",
typeof(void),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.SetBufferContents1:
return new RemoteHostMethodInfo(
@ -527,7 +527,7 @@ namespace System.Management.Automation.Remoting
typeof(IHostSupportsInteractiveSession),
"PopRunspace",
typeof(void),
new Type[] { });
Array.Empty<Type>());
// IHostSupportsInteractiveSession properties.
@ -536,14 +536,14 @@ namespace System.Management.Automation.Remoting
typeof(IHostSupportsInteractiveSession),
"get_IsRunspacePushed",
typeof(bool),
new Type[] { });
Array.Empty<Type>());
case RemoteHostMethodId.GetRunspace:
return new RemoteHostMethodInfo(
typeof(IHostSupportsInteractiveSession),
"get_Runspace",
typeof(System.Management.Automation.Runspaces.Runspace),
new Type[] { });
Array.Empty<Type>());
default:
Dbg.Assert(false, "All RemoteHostMethodId's should be handled. This code should not be reached.");

View file

@ -52,7 +52,10 @@ namespace System.Management.Automation
if (times == 0 || array.Length == 0)
{
return new T[0]; // don't use Utils.EmptyArray, always return a new array
#pragma warning disable CA1825 // Avoid zero-length array allocations
// Don't use Array.Empty<T>(); always return a new instance.
return new T[0];
#pragma warning restore CA1825 // Avoid zero-length array allocations
}
var context = LocalPipeline.GetExecutionContextFromTLS();

View file

@ -3228,7 +3228,10 @@ namespace System.Management.Automation
if (originalList.Count == 0)
{
return new object[0]; // don't use Utils.EmptyArray, always return a new array
#pragma warning disable CA1825 // Avoid zero-length array allocations
// Don't use Array.Empty<object>(); always return a new instance.
return new object[0];
#pragma warning restore CA1825 // Avoid zero-length array allocations
}
return ArrayOps.Multiply(originalList.ToArray(), times);

View file

@ -3814,7 +3814,7 @@ namespace Microsoft.PowerShell.Commands
value,
typeof(byte[]),
CultureInfo.CurrentCulture)
: new byte[] { };
: Array.Empty<byte>();
break;
case RegistryValueKind.DWord:
@ -3851,7 +3851,7 @@ namespace Microsoft.PowerShell.Commands
value,
typeof(string[]),
CultureInfo.CurrentCulture)
: new string[] { };
: Array.Empty<string>();
break;
case RegistryValueKind.QWord:

View file

@ -128,12 +128,12 @@ namespace System.Management.Automation.Internal
ConstructorInfo constructor = returnValue._graphicalHostHelperType.GetConstructor(
BindingFlags.NonPublic | BindingFlags.Instance,
null,
new Type[] { },
Array.Empty<Type>(),
null);
if (constructor != null)
{
returnValue._graphicalHostHelperObject = constructor.Invoke(new object[] { });
returnValue._graphicalHostHelperObject = constructor.Invoke(Array.Empty<object>());
Diagnostics.Assert(returnValue._graphicalHostHelperObject != null, "the constructor does not throw anything");
}
@ -187,7 +187,7 @@ namespace System.Management.Automation.Internal
Diagnostics.Assert(_graphicalHostHelperObject != null, "there should be a constructor in order to get an instance property value");
PropertyInfo property = _graphicalHostHelperType.GetProperty(propertyName, BindingFlags.NonPublic | BindingFlags.Instance);
Diagnostics.Assert(property != null, "property " + propertyName + " exists in graphicalHostHelperType is verified by caller");
return property.GetValue(_graphicalHostHelperObject, new object[] { });
return property.GetValue(_graphicalHostHelperObject, Array.Empty<object>());
}
/// <summary>
@ -199,7 +199,7 @@ namespace System.Management.Automation.Internal
{
PropertyInfo property = _graphicalHostHelperType.GetProperty(propertyName, BindingFlags.NonPublic | BindingFlags.Static);
Diagnostics.Assert(property != null, "property " + propertyName + " exists in graphicalHostHelperType is verified by caller");
return property.GetValue(null, new object[] { });
return property.GetValue(null, Array.Empty<object>());
}
/// <summary>

View file

@ -19,7 +19,7 @@ namespace PSTests.Parallel
{
var cpp = new CommandLineParameterParser();
cpp.Parse(new string[0]);
cpp.Parse(System.Array.Empty<string>());
Assert.False(cpp.AbortStartup);
Assert.Empty(cpp.Args);
@ -60,9 +60,9 @@ namespace PSTests.Parallel
{
var cpp = new CommandLineParameterParser();
cpp.Parse(new string[0]);
cpp.Parse(System.Array.Empty<string>());
Assert.Throws<System.InvalidOperationException>(() => cpp.Parse(new string[0]));
Assert.Throws<System.InvalidOperationException>(() => cpp.Parse(System.Array.Empty<string>()));
}
[Theory]