C#递归调用和数组
本文关键字:数组 调用 递归 | 更新日期: 2023-09-27 18:19:59
我坐在这里,发现自己正在为C#编写一个递归调用,以编写RegistryKey
。
这是我可以很容易地硬编码的东西,但我想递归地做。
using System;
using System.Collections.Generic;
using Microsoft.Win32;
private const string regKeyPath = @"Software'Apps'jp2code'net'TestApp";
static void Main() {
string[] split = regKeyPath.Split('''');
RegistryKey key = null;
try {
keyMaker(Registry.LocalMachine, split);
} finally {
if (key != null) {
key.Close();
}
}
// continue on with Application.Run(new Form1());
}
所以,keyMaker
就是我想要的递归函数。
private static void keyMaker(RegistryKey key, string[] path) {
string subKey = null;
string[] subKeyNames = key.GetSubKeyNames();
foreach (var item in subKeyNames) {
if (path[0] == item) {
subKey = item;
}
}
RegistryKey key2 = null;
try {
if (String.IsNullOrEmpty(subKey)) {
key2 = key.CreateSubKey(subKey);
} else {
key2 = key.OpenSubKey(subKey);
}
keyMaker(key2, &path[1]); // <= NOTE! Not allowed/defined in C#
} finally {
key2.Close();
}
}
因此,我不能简单地从数组的下一个元素开始传递数组。
在C#中有一种巧妙的方法可以做到这一点吗?
Registry位与问题无关,而是将我的真实世界问题添加到数组任务中。
一种简单的方法是更改方法的签名以包含起始索引:
void keyMaker(RegistryKey key, string[] path, int startIndex)
除此之外,您可以使用LinkedList<T>
或Queue<T>
来代替数组,并使用LinkedList<T>.RemoveFirst()
或Queue<T>.Dequeue()
方法来移除它们的头元素。
但您根本不需要递归来解决这个问题(除非这是一个练习)。
不要递归就是全部。以下是我的编写方法,假设密钥只由CreateSubKey
返回(如果存在):
private static void keyMaker(RegistryKey key, string[] path) {
foreach(string subkey in path) {
key = key.CreateSubKey(subkey);
}
}
如果立即关闭它们很重要(我对此表示怀疑):
private static void keyMaker(RegistryKey key, string[] path) {
RegistryKey lastKey = key;
foreach(string subkey in path) {
key = key.CreateSubKey(subkey);
lastKey.Close();
lastKey = key;
}
lastKey.Close();
}
虽然我更喜欢像@Groo建议的那样传递索引,但另一种可能性是使用IEnumerable<string>
而不是string[]
并使用LINQ。在递归调用中,您可以传递path.Skip(1)
,它将从列表中删除第一个元素(或者,更准确地说,返回从第二个元素开始的新IEnumerable<string>
)。
根据LOL编辑。
keyMaker(Registry.LocalMachine, ref split, 0);
....
private static void keyMaker(RegistryKey key, ref string[] path, int index) {
if( index > path.length - 1 ) return;
....
if (path[index] == item) {
....
keyMaker(key2, ref path, ++index);
....