Это мой класс:
public class UnusedRolesOccurrence
{
public string Username { get; set; }
public string FullName { get; set; }
public string Role { get; set; }
public int[] Month { get { return month; } set { month = value; } }
private static int[] month = new int[12];
}
И здесь я хочу заполнить массив int значениями:
Parallel.ForEach(unusedrolesoccurrence, (UnusedRolesOccurrence item) =>
{
try
{
lock (listLock)
{
int count = tmp.Count(x => x.Username == item.Username && x.Role == item.Role);
item.Month[month] = count;
if (count > 2)
{
Debug.WriteLine($"{item.Username},{item.Role},{month}={count},{item.Month[month]}");
}
}
}
catch
{
//
}
});
List<unusedrolesoccurrence>
предварительно заполняется данными. Месяц массив [0,0,0,0,0,0,0,0,0,0,0,0] перед началом foreach, с int[] arr_month = new int[12];
.
tmp
также является List<t>
.
Что не работает: во время цикла число, а также значение item.Month[month]
является правильным. Но не в цель List<UnusedRolesOccurrence>
. Все месяцы - это одно и то же значение последнего счета, обработанного в цикле, например [3,0,3,0,0,0,0,0,0,0,0,0] или [0,1,1,0,0,0,0,0,0,0,0,0 ]. И потому, что параллельно, это всегда другой результат, конечно.
Я изменил int[]
на public Dictionary<int, int> Month { get; set; }
для тестирования, но такое же поведение.
ЗДЕСЬ ПРИМЕР КОДА (с // вторичной попыткой со словарем с тем же результатом):
public class UnusedRoles
{
public string Username { get; set; }
public string Role { get; set; }
public int Month { get; set; }
}
public class UnusedRolesOccurrence
{
public string Username { get; set; }
public string Role { get; set; }
//public Dictionary<int, int> Month { get; set; }
public int[] Month { get { return month; } set { month = value; } }
public int[] month = new int[12];
}
public List<UnusedRoles> unusedroles = new List<UnusedRoles>();
public List<UnusedRolesOccurrence> unusedrolesoccurrence = new List<UnusedRolesOccurrence>();
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
Run();
}
public async void Run()
{
unusedroles.Clear();
unusedrolesoccurrence.Clear();
Dictionary<int, int> dictionary_month = new Dictionary<int, int>();
//for (int i = 0; i < 12; i++) { dictionary_month.Add(i, 0); }
int[] arr_month = new int[12];
unusedroles.Add(new UnusedRoles { Username = "User1", Role = "A", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User1", Role = "A", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User1", Role = "B", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User2", Role = "A", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User2", Role = "B", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User2", Role = "B", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User3", Role = "C", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User3", Role = "C", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User3", Role = "C", Month = 0 });
unusedroles.Add(new UnusedRoles { Username = "User4", Role = "A", Month = 0 });
var tmp = unusedroles.Select(x => new { x.Username, x.Role }).Distinct();
foreach (var item in tmp)
{
unusedrolesoccurrence.Add(new UnusedRolesOccurrence
{
//Username = item.Username, Role = item.Role, Month = dictionary_month
Username = item.Username, Role = item.Role, Month = arr_month
});
}
var result = await Find(0);
foreach (var item in unusedrolesoccurrence)
{
//string line = "";
//foreach (var pair in item.Month) {
// line = $"{line},{pair.Value}";
//}
string line = $"{item.Username},{item.Role}";
foreach (int i in item.Month)
{
line = $"{line},{i}";
}
//Debug.WriteLine($"{item.Username},{item.Role}{line}");
Debug.WriteLine($"{line}");
}
}
public async Task<bool> Find(int month)
{
await Task.Run(() =>
{
Parallel.ForEach(unusedrolesoccurrence, (UnusedRolesOccurrence item) =>
{
int count = unusedroles.Count(x => x.Username == item.Username && x.Role == item.Role &&x.Month == month);
item.Month[month] = count;
Debug.WriteLine($"{item.Username},{item.Role},count={count},item.Month[{month}]={item.Month[month]}");
});
});
return true;
}