Published - Added Mapping shortcut,

added leveled limits, container bug fix,
This commit is contained in:
Mike Phares 2022-09-25 20:17:19 -07:00
parent d789f295c6
commit a145a89112
17 changed files with 416 additions and 262 deletions

28
.vscode/launch.json vendored
View File

@ -81,3 +81,31 @@
// https://scontent-lax3-2.xx.fbcdn.net/v/t31.18172-8/10887668_10205175511939476_7644367668075304275_o.jpg?_nc_cat=100&ccb=1-7&_nc_sid=730e14&_nc_ohc=2T_utQvqkXYAX94o-WV&_nc_ht=scontent-lax3-2.xx&oh=00_AT8aSCQ4JVgRULd1RxRJ8DYqPtB9EyGY-May2QwwqKSqjQ&oe=6356B098
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/78675669_10102984650797787_175454688261439488_n.jpg?_nc_cat=101&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=7Plv_RW77xoAX9PiH9G&_nc_ht=scontent-lax3-2.xx&oh=00_AT-npzVNkTzAdYgQ4D1ltfyl8llC_xqOHJ9Mi8Vmh2khlw&oe=63571251
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/59569741_10214142910059142_9219208491263066112_n.jpg?_nc_cat=100&ccb=1-7&_nc_sid=730e14&_nc_ohc=F7GF2uCFljcAX8Skffr&_nc_ht=scontent-lax3-2.xx&oh=00_AT9e3f8x6hSmAcxQ5JDUvDPFEg0wcecKw175Qfj_WMwADQ&oe=635488AA
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/290559432_10209959340897099_842876274165104077_n.jpg?_nc_cat=111&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=Vgxc93JsPBEAX8zrKaq&_nc_ht=scontent-lax3-2.xx&oh=00_AT-pPGd4o-t7kSeY4XKOTDeOzfg6wXOMBdY6rldQyrKQmw&oe=6335398E
// https://scontent-lax3-1.xx.fbcdn.net/v/t39.30808-6/308587069_10210153867920153_6202104893656263114_n.jpg?stp=cp6_dst-jpg&_nc_cat=104&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=SKB2FSdXFQEAX_v1t5g&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-1.xx&oh=00_AT_E1y9uQ27O5_FAyAeRJ0XotEyBEXytkM2iDCGvldSxLw&oe=633549B9
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/67309987_10214298629206292_6820175905885782016_n.jpg?_nc_cat=106&ccb=1-7&_nc_sid=730e14&_nc_ohc=BTQEZF_dwRwAX-cxNEm&_nc_ht=scontent-lax3-2.xx&oh=00_AT8_z-JOBPmskVsJ0S9bOYgcYngpVrMjhVrfFk3r06Wj8Q&oe=635473AE
// https://scontent-lax3-1.xx.fbcdn.net/v/t39.30808-6/263710427_1324163581376203_7502850514450466967_n.jpg?_nc_cat=110&ccb=1-7&_nc_sid=e3f864&_nc_ohc=2KB9VISs3y0AX-PiYUd&_nc_ht=scontent-lax3-1.xx&oh=00_AT_WaHBBSAR2-1dDEdpufugFf4eBttyGfIIflCwvCu_76g&oe=6334DBC3
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/67181620_114720179834180_3651229536021905408_n.jpg?_nc_cat=101&ccb=1-7&_nc_sid=09cbfe&_nc_ohc=CYF8Qyy506MAX-GBXV_&_nc_ht=scontent-lax3-2.xx&oh=00_AT_dFZiY42lloSfdiqNgSBlDpS9eGIEu85hhG5KIQD7DwA&oe=6354B320
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.6435-9/68383564_10217654576270105_5209606295652401152_n.jpg?_nc_cat=109&ccb=1-7&_nc_sid=730e14&_nc_ohc=phqcunpNs5EAX-d33kB&_nc_ht=scontent-lax3-1.xx&oh=00_AT9n5kFQnIPSXUzNAMb19Wpue1YA-bHFpSCE-_tOXD8Gnw&oe=635615C2
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/285466259_7423531907720135_1229107015631332741_n.jpg?_nc_cat=111&ccb=1-7&_nc_sid=09cbfe&_nc_ohc=z85uLRC706sAX_H3_Ht&_nc_ht=scontent-lax3-2.xx&oh=00_AT-_wJpeYhqcdivdF4SbBO3B6M082qGD3qdGAPDmVP6nAA&oe=6334B2ED
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.6435-9/32919393_10214483292069982_3789509822047584256_n.jpg?_nc_cat=105&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=oJzHahluIDYAX-5-UGl&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-1.xx&oh=00_AT9e7dHUoseqwf6qF39NHEnPzal6NzQgyCwio6SvzUZTUQ&oe=63575682
// https://scontent-lax3-1.xx.fbcdn.net/v/t31.18172-8/22256636_1931521070438917_6414682443902494017_o.jpg?_nc_cat=102&ccb=1-7&_nc_sid=cdbe9c&_nc_ohc=bf99qSpRJOQAX_stzg5&_nc_ht=scontent-lax3-1.xx&oh=00_AT-eoWkn2Gaqj8BGasgNOycRzf3AiQE2GqHtKC28_-vFug&oe=63586C84
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.18169-9/600876_10151927436713567_876993105_n.jpg?_nc_cat=110&ccb=1-7&_nc_sid=cdbe9c&_nc_ohc=dcNCC6RNOooAX985ENZ&_nc_ht=scontent-lax3-1.xx&oh=00_AT-9Q999B_sWiS-yPP48gVdrheH0bY-DAiOKmkExbnW5Rw&oe=6355ED8A
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.6435-9/35235266_10213962597433782_6655457381733892096_n.jpg?_nc_cat=110&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=uxfDliBhPHUAX_JXJNU&_nc_ht=scontent-lax3-1.xx&oh=00_AT9zGc-8QqaAHItoDqGzKAMEYOU0fEQz_ld1R_CGxPokug&oe=63565840
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.6435-9/161932468_10159007128985149_3980438021322511452_n.jpg?_nc_cat=104&ccb=1-7&_nc_sid=09cbfe&_nc_ohc=6dCTPFwvFPcAX8ogdv8&_nc_ht=scontent-lax3-1.xx&oh=00_AT8pspicXFXgj-MOKzkTyp_ZpuboruYwyM-MMNwro_m9JA&oe=63564482
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.6435-9/91250196_10215323899906785_1298078522899693568_n.jpg?_nc_cat=110&ccb=1-7&_nc_sid=730e14&_nc_ohc=CSXhKF_1hqsAX9qlbvP&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-1.xx&oh=00_AT-JZSnju_3XqWV6w9rSSUmuo2oIaCig5pn7JmrvFbBfGw&oe=6354B339
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.18169-9/428510_490436967638912_1438526428_n.jpg?_nc_cat=108&ccb=1-7&_nc_sid=ba80b0&_nc_ohc=s0ZgvdtWwOsAX87AD-I&_nc_ht=scontent-lax3-1.xx&oh=00_AT-gv7QKuJhEjRPbmQr5hLG163-EQXcx6FJ8aHCcPTfEXw&oe=63563591
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/50312617_10161338488075048_5525340242208358400_n.jpg?_nc_cat=101&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=NcQcK_z6t9kAX9-On7t&_nc_ht=scontent-lax3-2.xx&oh=00_AT_WYrFNqGwzuSssGPBRmhpqGlyf1k2ulbdKakrs4xAHBg&oe=635832DB
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/247966826_10200232179385908_1907223790607385605_n.jpg?_nc_cat=106&ccb=1-7&_nc_sid=09cbfe&_nc_ohc=Xn0j5rxLaCQAX8OD7k4&_nc_ht=scontent-lax3-2.xx&oh=00_AT_bVVWAuaGYpIcBOCbAtn_xyS2Rqu--uKs06-FKOfjuzg&oe=633583B8
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/57840024_10161651547530207_1744748790901899264_n.jpg?_nc_cat=107&ccb=1-7&_nc_sid=730e14&_nc_ohc=TKg3rTiXkYUAX-V8NO5&_nc_ht=scontent-lax3-2.xx&oh=00_AT-Mepp0iN8-mHhyKRHj-R5yBOu2wZGtQeApkSoZTzM3mg&oe=6356A1D2
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/269876615_612483726673361_2182050585964176784_n.jpg?_nc_cat=106&ccb=1-7&_nc_sid=174925&_nc_ohc=9QJt0X_FDlEAX_Okew3&_nc_ht=scontent-lax3-2.xx&oh=00_AT_Yq8OflcYUA39JsmM__UxFYi8YASqsrRYx-T1Qn2NPSw&oe=6336391B
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/126332086_10224303272989365_2242003924983097751_n.jpg?_nc_cat=111&ccb=1-7&_nc_sid=09cbfe&_nc_ohc=zpX0nadZ9XMAX8m1Kk1&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-2.xx&oh=00_AT9c_dq-TLiNxgeqmp9Pwnqp9xjUIG3_ijxmiAW4MPYBKw&oe=63578DD6
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/74624149_10215957575592842_7757392320252608512_n.jpg?_nc_cat=103&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=22WGGAPeTdAAX87greQ&_nc_ht=scontent-lax3-2.xx&oh=00_AT9J2qV9zBMEPuqsibA-87pjTBg3e3hVwHb211GO7lJicQ&oe=6355F050
// https://scontent-lax3-1.xx.fbcdn.net/v/t31.18172-8/10649011_812346452173040_8035951943727654673_o.jpg?_nc_cat=104&ccb=1-7&_nc_sid=84a396&_nc_ohc=aDP-7N5XOgMAX9eflUn&_nc_ht=scontent-lax3-1.xx&oh=00_AT_mCAWB-OTJ32F1W90m-bPWu9GmjvFr-j1VdAQmkdNtXg&oe=63565628
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/289655024_10228170790084748_4126077972169573791_n.jpg?_nc_cat=101&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=NeX9XD5pcwMAX9UBHLe&_nc_ht=scontent-lax3-2.xx&oh=00_AT-Qh77ATMIGL6JnKHr9rIim3Ui_UU7XH_S02S7-iu21qg&oe=633700F0
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/266998682_10227151119593623_456420668145746211_n.jpg?_nc_cat=101&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=vjNb4pBYn5YAX_gWfIx&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-2.xx&oh=00_AT_rv-lqoI2u7Y-FMU8G8Vfxo6QyA-tTEIMKRpRx9TxZPg&oe=63353CCC
// https://scontent-lax3-1.xx.fbcdn.net/v/t1.6435-9/40093120_10217172129645111_2951374557987995648_n.jpg?_nc_cat=110&ccb=1-7&_nc_sid=8bfeb9&_nc_ohc=X1j0ykpT26oAX8kDzfQ&_nc_ht=scontent-lax3-1.xx&oh=00_AT-jst6eXb7F4NsSJRj4jOQvKqQOiiMP4K5iT8xq2t4dTg&oe=63588214
// https://scontent-lax3-2.xx.fbcdn.net/v/t1.6435-9/31870362_10216285257993874_8330563136197230592_n.jpg?_nc_cat=103&ccb=1-7&_nc_sid=84a396&_nc_ohc=8kJ5pbwsKDMAX9hIVFA&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-2.xx&oh=00_AT9vRjGUZdT7KasJ4Ndti2LHfrPaTcahl4ipT9BmdRZJeg&oe=6356737F
// https://scontent-lax3-2.xx.fbcdn.net/v/t39.30808-6/230074448_10103880528811228_6909448863476427135_n.jpg?_nc_cat=103&ccb=1-7&_nc_sid=0debeb&_nc_ohc=cUpp1Y_DO8MAX92tN_t&tn=D0unuoVdv--xjhpM&_nc_ht=scontent-lax3-2.xx&oh=00_AT-K2_yEERUmvvjkjUKf7zwaV2Ofq1fHIQAtEkCt7I2Bhw&oe=63352B95
// https://scontent-lax3-2.xx.fbcdn.net/v/t31.18172-8/13502600_10210212049485607_95598559411189791_o.jpg?_nc_cat=101&ccb=1-7&_nc_sid=cdbe9c&_nc_ohc=AEojM0a2X5cAX8kmHfZ&_nc_ht=scontent-lax3-2.xx&oh=00_AT-ZX7vIfwazh_zcDpFCLxwLgp90gERyBG2CtGxIClEnYA&oe=6355A9C7
// https://scontent-lax3-2.xx.fbcdn.net/v/t31.18172-8/14195939_1314130471931770_9026437168267009241_o.jpg?_nc_cat=106&ccb=1-7&_nc_sid=730e14&_nc_ohc=f8owaBX7kMQAX8ioj3m&_nc_ht=scontent-lax3-2.xx&oh=00_AT8N8GR4GXmKa3w_dP952fl1_bx_s7CTz8qFtxaBK91S2w&oe=6355DBA1

View File

@ -39,33 +39,101 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
if (!Directory.Exists(eDistanceContentCollectionDirectory))
_ = Directory.CreateDirectory(eDistanceContentCollectionDirectory);
#pragma warning disable
string[] results = (from l in sortingContainers select string.Concat(l.Sorting.WithinRange, '\t', l.Sorting.DistancePermyriad, '\t', l.Sorting.DaysDelta, '\t', l.Sorting.Id, '\t', l.Sorting.NormalizedPixelPercentage, '\t', l.Sorting.Older, '\t', l.Face.Mapping.MappingFromItem.Id, '\t', l.Face.Mapping.MappingFromLocation.NormalizedPixelPercentage)).ToArray();
string[] results = (from l in sortingContainers select l.ToString()).ToArray();
#pragma warning restore
string eDistanceContentFileName = Path.Combine(eDistanceContentCollectionDirectory, $"{configuration.ResultAllInOne}.tvs");
File.WriteAllLines(eDistanceContentFileName, results);
}
private List<Sorting> GetSortingCollection(MapLogic mapLogic, List<FaceDistance> faceDistanceEncodings, int faceDistanceContainersLength, int i, FaceDistance faceDistanceEncoding)
private static List<Sorting> GetSortingCollection(MapLogic mapLogic, List<FaceDistance> faceDistanceEncodings, int faceDistanceContainersLength, int i, FaceDistance faceDistanceEncoding)
{
List<Sorting> results;
List<FaceDistance> faceDistanceLengths = FaceRecognition.FaceDistances(faceDistanceEncodings, faceDistanceEncoding);
if (faceDistanceLengths.Count != faceDistanceContainersLength)
throw new NotSupportedException();
bool anyLowerThanTolerance = (from l in faceDistanceLengths where l.Length is not null && l.Length.Value != 0 && l.Length.Value < _FaceDistanceTolerance select true).Any();
results = mapLogic.GetSortingCollection(i, faceDistanceEncoding, faceDistanceLengths, anyLowerThanTolerance);
results = mapLogic.GetSortingCollection(i, faceDistanceEncoding, faceDistanceLengths);
return results;
}
private List<SortingContainer> GetSortingContainers(Face face, FaceDistance faceDistanceEncoding, List<Sorting> sortingCollection)
private List<SortingContainer> GetSortingContainers(Face face, FaceDistance faceDistanceEncoding, List<Sorting> sortingCollection, int? useFiltersCounter)
{
List<SortingContainer> results = new();
SortingContainer sortingContainer;
Sorting[] collection = Shared.Models.Stateless.Methods.ISorting.Sort(sortingCollection);
double faceDistancePermyriad;
double sortingDaysDeltaTolerance;
double faceDistanceMinimumConfidence;
if (useFiltersCounter is null)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance;
faceDistancePermyriad = _FaceDistancePermyriad;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence;
}
else if (useFiltersCounter.Value == 1)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5;
faceDistancePermyriad = _FaceDistancePermyriad;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence;
}
else if (useFiltersCounter.Value == 2)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance;
faceDistancePermyriad = _FaceDistancePermyriad * 1.5;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence;
}
else if (useFiltersCounter.Value == 3)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance;
faceDistancePermyriad = _FaceDistancePermyriad;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5;
}
else if (useFiltersCounter.Value == 4)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2;
faceDistancePermyriad = _FaceDistancePermyriad * 1.5;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5;
}
else if (useFiltersCounter.Value == 5)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5;
faceDistancePermyriad = _FaceDistancePermyriad * 2;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .5;
}
else if (useFiltersCounter.Value == 6)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 1.5;
faceDistancePermyriad = _FaceDistancePermyriad * 1.5;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25;
}
else if (useFiltersCounter.Value == 7)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2.5;
faceDistancePermyriad = _FaceDistancePermyriad * 2;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25;
}
else if (useFiltersCounter.Value == 8)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2;
faceDistancePermyriad = _FaceDistancePermyriad * 2.5;
faceDistanceMinimumConfidence = _FaceDistanceMinimumConfidence * .25;
}
else if (useFiltersCounter.Value == 9)
{
sortingDaysDeltaTolerance = _SortingDaysDeltaTolerance * 2;
faceDistancePermyriad = _FaceDistancePermyriad * 2;
faceDistanceMinimumConfidence = 0;
}
else
{
sortingDaysDeltaTolerance = int.MaxValue;
faceDistancePermyriad = int.MaxValue;
faceDistanceMinimumConfidence = 0;
}
foreach (Sorting sorting in collection)
{
if (face.Mapping is null || faceDistanceEncoding.NormalizedPixelPercentage is null)
throw new NotSupportedException();
if (face.Mapping.MappingFromLocation.Confidence < _FaceDistanceMinimumConfidence || sorting.DistancePermyriad > _FaceDistancePermyriad || sorting.DaysDelta > _SortingDaysDeltaTolerance)
if (sorting.DaysDelta > sortingDaysDeltaTolerance || sorting.DistancePermyriad > faceDistancePermyriad || face.Mapping.MappingFromLocation.Confidence < faceDistanceMinimumConfidence)
continue;
sortingContainer = new(face, sorting);
results.Add(sortingContainer);
@ -116,7 +184,7 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
return faceDistanceEncodings;
}
public SortingContainer[] SetFaceMappingSortingCollectionThenGetSortingContainers(int maxDegreeOfParallelism, long ticks, MapLogic mapLogic, Face[] selectedFilteredFaces)
public SortingContainer[] SetFaceMappingSortingCollectionThenGetSortingContainers(int maxDegreeOfParallelism, long ticks, MapLogic mapLogic, Face[] selectedFilteredFaces, int? useFiltersCounter)
{
SortingContainer[] results;
List<SortingContainer> collection = new();
@ -126,8 +194,6 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
List<FaceDistance> faceDistanceEncodings = GetFaceDistanceEncodings(faceDistanceContainers);
string message = $") {faceDistanceContainers.Length:000} Get Sorting Containers Then Set Face Mapping Sorting Collection - {totalSeconds} total second(s)";
ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true };
foreach (Face face in selectedFilteredFaces)
face.ClearFaceDistance();
using ProgressBar progressBar = new(faceDistanceContainers.Length, message, options);
_ = Parallel.For(0, faceDistanceContainers.Length, parallelOptions, (i, state) =>
{
@ -136,14 +202,22 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
if (face.Mapping is null)
throw new NotSupportedException();
FaceDistance faceDistanceEncoding = faceDistanceContainers[i].FaceDistance;
if (mapLogic.Used(faceDistanceEncoding))
return;
List<Sorting> sortingCollection = GetSortingCollection(mapLogic, faceDistanceEncodings, faceDistanceContainers.Length, i, faceDistanceEncoding);
List<SortingContainer> sortingContainers = GetSortingContainers(face, faceDistanceEncoding, sortingCollection);
lock (collection)
collection.AddRange(sortingContainers);
lock (face)
face.ReleaseFaceDistance();
if (!sortingCollection.Any())
return;
List<SortingContainer> sortingContainers = GetSortingContainers(face, faceDistanceEncoding, sortingCollection, useFiltersCounter);
if (sortingContainers.Any())
{
lock (collection)
collection.AddRange(sortingContainers);
}
});
results = Shared.Models.Stateless.Methods.ISortingContainer.Sort(collection);
if (!collection.Any())
results = Array.Empty<SortingContainer>();
else
results = Shared.Models.Stateless.Methods.ISortingContainer.Sort(collection);
return results;
}
@ -458,21 +532,23 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
return results;
}
private static FileInfo? CheckFileThenGetFileInfo(string facesFileNameExtension, Item item, string mappedFaceDirectory, string mappedFaceFile, List<Face> checkFaces)
private static FileInfo? CheckFileThenGetFileInfo(string facesFileNameExtension, MappingFromItem mappingFromItem, string mappedFaceFile, List<Face> checkFaces)
{
FileInfo? result = null;
string checkFile;
string? mappedFaceDirectory;
string deterministicHashCodeKey;
foreach (Face face in checkFaces)
{
if (checkFaces.Count != 1)
break;
if (item.Property?.Id is null || item.ImageFileHolder is null)
throw new NotSupportedException();
if (face.FaceEncoding is null || face.Location is null || face.OutputResolution is null)
throw new NotSupportedException();
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(item.Property.Id.Value, face.Location, Shared.Models.Stateless.ILocation.Digits, Shared.Models.Stateless.ILocation.Factor, face.OutputResolution);
checkFile = Path.Combine(mappedFaceDirectory, $"{deterministicHashCodeKey}{item.ImageFileHolder.ExtensionLowered}{facesFileNameExtension}");
mappedFaceDirectory = Path.GetDirectoryName(mappedFaceFile);
if (mappedFaceDirectory is null)
throw new NotSupportedException();
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(mappingFromItem.Id, face.Location, Shared.Models.Stateless.ILocation.Digits, Shared.Models.Stateless.ILocation.Factor, face.OutputResolution);
checkFile = Path.Combine(mappedFaceDirectory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{facesFileNameExtension}");
if (checkFile == mappedFaceFile)
continue;
result = new FileInfo(checkFile);
@ -510,54 +586,25 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
return results;
}
public (int, int, int) GetUnableToMatchCountAndRenameMatches(string facesFileNameExtension, string eDistanceContentDirectory, Item item, List<Face> faces, string[] mappedFaceFiles)
public (int, int, int) GetUnableToMatchCountAndRenameMatches(string facesFileNameExtension, string eDistanceContentDirectory, MappingFromItem mappingFromItem, List<Face> faces, List<(string MappedFaceFile, int normalizedPixelPercentage)> collection)
{
int result = 0;
int? id;
string? json;
int renamed = 0;
bool? isWrongYear;
FileInfo? fileInfo;
DateTime minimumDateTime;
string? mappedFaceDirectory;
List<Face> checkFaces = new();
List<int> debugChecks = new();
int? normalizedPixelPercentage;
MappingFromItem mappingFromItem;
List<int> normalizedPixelPercentages;
List<int> normalizedPixelPercentages = new();
List<string> duplicateMappedFaceFiles = new();
Dictionary<int, List<int>> idToNormalizedPixelPercentages = new();
foreach (string mappedFaceFile in mappedFaceFiles)
string[] mappedFaceFiles = (from l in collection select l.MappedFaceFile).ToArray();
foreach ((string mappedFaceFile, int normalizedPixelPercentage) in collection)
{
mappedFaceDirectory = Path.GetDirectoryName(mappedFaceFile);
if (mappedFaceDirectory is null)
throw new NotSupportedException();
if (item.Property?.Id is null)
throw new NotSupportedException();
if (duplicateMappedFaceFiles.Contains(mappedFaceFile))
continue;
(id, normalizedPixelPercentage, _) = Shared.Models.Stateless.Methods.IMapping.GetReversedDeterministicHashCodeKey(facesFileNameExtension, mappedFaceFile);
if (id is null || normalizedPixelPercentage is null)
{
result++;
continue;
}
if (id.Value != item.Property.Id.Value)
continue;
if (item.Property?.Id is null || item.ImageFileHolder is null || item.ResizedFileHolder is null)
continue;
if (faces.Any(l => l.FaceEncoding is null || l.Location is null || l.OutputResolution is null))
continue;
minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property);
(isWrongYear, _) = item.Property.IsWrongYear(item.ImageFileHolder.FullName, minimumDateTime);
mappingFromItem = new(item.Property.Id.Value, item.ImageFileHolder, isWrongYear, minimumDateTime, item.ResizedFileHolder);
json = null;
checkFaces.Clear();
debugChecks.Clear();
if (!idToNormalizedPixelPercentages.ContainsKey(id.Value))
idToNormalizedPixelPercentages.Add(id.Value, new());
normalizedPixelPercentages = idToNormalizedPixelPercentages[id.Value];
checkFaces.AddRange(GetMatchingFaces(faces, mappedFaceFiles, debugChecks, normalizedPixelPercentage.Value, normalizedPixelPercentages, duplicateMappedFaceFiles, mappedFaceFile));
checkFaces.AddRange(GetMatchingFaces(faces, mappedFaceFiles, debugChecks, normalizedPixelPercentage, normalizedPixelPercentages, duplicateMappedFaceFiles, mappedFaceFile));
if (checkFaces.Count != 1)
{
checkFaces.Clear();
@ -599,8 +646,8 @@ public class E_Distance : Shared.Models.Methods.IFaceDistance
MoveUnableToMatch(eDistanceContentDirectory, mappedFaceFile);
continue;
}
normalizedPixelPercentages.Add(normalizedPixelPercentage.Value);
fileInfo = CheckFileThenGetFileInfo(facesFileNameExtension, item, mappedFaceDirectory, mappedFaceFile, checkFaces);
normalizedPixelPercentages.Add(normalizedPixelPercentage);
fileInfo = CheckFileThenGetFileInfo(facesFileNameExtension, mappingFromItem, mappedFaceFile, checkFaces);
if (fileInfo is null)
continue;
File.Move(mappedFaceFile, fileInfo.FullName);

View File

@ -175,32 +175,28 @@ public class D_Face
}
}
private List<Shared.Models.Face> GetFaces(Item item, Shared.Models.Property property, int outputResolutionWidth, int outputResolutionHeight, int outputResolutionOrientation)
private List<Shared.Models.Face> GetFaces(Shared.Models.Property property, MappingFromItem mappingFromItem, int outputResolutionWidth, int outputResolutionHeight, int outputResolutionOrientation)
{
List<Shared.Models.Face> results = new();
if (item.ImageFileHolder is null)
throw new NullReferenceException(nameof(item.ImageFileHolder));
if (item.ResizedFileHolder is null)
throw new NullReferenceException(nameof(item.ResizedFileHolder));
FaceRecognitionDotNet.Image? unknownImage;
if (!item.ResizedFileHolder.Exists)
if (!mappingFromItem.ResizedFileHolder.Exists)
unknownImage = null;
else
{
try
{ unknownImage = FaceRecognition.LoadImageFile(item.ResizedFileHolder.FullName); }
{ unknownImage = FaceRecognition.LoadImageFile(mappingFromItem.ResizedFileHolder.FullName); }
catch (Exception)
{ unknownImage = null; }
}
if (unknownImage is null)
results.Add(new(property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation, item.RelativePath, location: null));
results.Add(new(property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation, mappingFromItem.RelativePath, location: null));
else
{
List<(Location Location, FaceRecognitionDotNet.FaceEncoding? FaceEncoding, Dictionary<FacePart, FacePoint[]>? FaceParts)> collection;
FaceRecognition faceRecognition = new(_NumberOfTimesToUpsample, _NumberOfJitters, _PredictorModel, _Model, _ModelParameter);
collection = faceRecognition.GetCollection(unknownImage, includeFaceEncoding: true, includeFaceParts: true);
if (!collection.Any())
results.Add(new(property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation, item.RelativePath, location: null));
results.Add(new(property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation, mappingFromItem.RelativePath, location: null));
else
{
double[] rawEncoding;
@ -208,7 +204,7 @@ public class D_Face
Shared.Models.FaceEncoding convertedFaceEncoding;
foreach ((Location location, FaceRecognitionDotNet.FaceEncoding? faceEncoding, Dictionary<FacePart, FacePoint[]>? faceParts) in collection)
{
face = new(property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation, item.RelativePath, location);
face = new(property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation, mappingFromItem.RelativePath, location);
if (faceEncoding is not null)
{
rawEncoding = faceEncoding.GetRawEncoding();
@ -230,20 +226,16 @@ public class D_Face
#pragma warning restore CA1416
public List<Shared.Models.Face> GetFaces(string dResultsFullGroupDirectory, List<Tuple<string, DateTime>> subFileTuples, List<string> parseExceptions, Item item, Shared.Models.Property property, int outputResolutionWidth, int outputResolutionHeight, int outputResolutionOrientation)
public List<Shared.Models.Face> GetFaces(string dResultsFullGroupDirectory, List<Tuple<string, DateTime>> subFileTuples, List<string> parseExceptions, Shared.Models.Property property, MappingFromItem mappingFromItem, int outputResolutionWidth, int outputResolutionHeight, int outputResolutionOrientation)
{
List<Shared.Models.Face>? results;
if (item.Property?.Id is null)
throw new NullReferenceException(nameof(item.Property.Id));
if (item.ImageFileHolder is null)
throw new NullReferenceException(nameof(item.ImageFileHolder));
if (string.IsNullOrEmpty(dResultsFullGroupDirectory))
throw new NullReferenceException(nameof(dResultsFullGroupDirectory));
string json;
string[] changesFrom = new string[] { nameof(A_Property), nameof(B_Metadata), nameof(C_Resize) };
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
string usingRelativePath = Path.Combine(AngleBracketCollection[0].Replace("<>", "[]"), $"{item.ImageFileHolder.NameWithoutExtension}.json");
string dCollectionFile = Path.Combine(dResultsFullGroupDirectory, "[]", _Configuration.ResultAllInOne, $"{item.Property.Id.Value}{item.ImageFileHolder.ExtensionLowered}.json");
string usingRelativePath = Path.Combine(AngleBracketCollection[0].Replace("<>", "[]"), $"{mappingFromItem.ImageFileHolder.NameWithoutExtension}.json");
string dCollectionFile = Path.Combine(dResultsFullGroupDirectory, "[]", _Configuration.ResultAllInOne, $"{mappingFromItem.Id}{mappingFromItem.ImageFileHolder.ExtensionLowered}.json");
FileInfo fileInfo = new(dCollectionFile);
if (!fileInfo.Exists)
{
@ -299,7 +291,7 @@ public class D_Face
if (results is null || (_RetryImagesWithoutAFace && results.Count == 1 && results[0].FaceEncoding is null))
{
bool wasNull = results is null;
results = GetFaces(item, property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation);
results = GetFaces(property, mappingFromItem, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation);
if (wasNull || (!wasNull && results.Any(l => l.FaceEncoding is not null)))
{
json = JsonSerializer.Serialize(results, _WriteIndentedAndWhenWritingNull);
@ -325,31 +317,27 @@ public class D_Face
return results;
}
public void SaveFaces(string dResultsFullGroupDirectory, List<Tuple<string, DateTime>> subFileTuples, List<string> parseExceptions, Item item, List<Shared.Models.Face> faces)
public void SaveFaces(string dResultsFullGroupDirectory, List<Tuple<string, DateTime>> subFileTuples, List<string> parseExceptions, MappingFromItem mappingFromItem, List<Shared.Models.Face> faces)
{
if (item.ImageFileHolder is null)
throw new NullReferenceException(nameof(item.ImageFileHolder));
if (item.ResizedFileHolder is null)
throw new NullReferenceException(nameof(item.ResizedFileHolder));
FileInfo fileInfo;
bool check = false;
string parentCheck;
string deterministicHashCodeKey;
List<(Shared.Models.Face, FileInfo?, string)> collection = new();
string[] changesFrom = new string[] { nameof(A_Property), nameof(B_Metadata), nameof(C_Resize) };
string facesDirectory = Path.Combine(AngleBracketCollection[0].Replace("<>", "()"), item.ImageFileHolder.NameWithoutExtension);
string facesDirectory = Path.Combine(AngleBracketCollection[0].Replace("<>", "()"), mappingFromItem.ImageFileHolder.NameWithoutExtension);
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
if (!Directory.Exists(facesDirectory))
_ = Directory.CreateDirectory(facesDirectory);
foreach (Shared.Models.Face face in faces)
{
if (item.Property?.Id is null || face.FaceEncoding is null || face.Location is null || face.OutputResolution is null)
if (face.FaceEncoding is null || face.Location is null || face.OutputResolution is null)
{
collection.Add(new(face, null, string.Empty));
continue;
}
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(item.Property.Id.Value, face.Location, ILocation.Digits, ILocation.Factor, face.OutputResolution);
fileInfo = new FileInfo(Path.Combine(facesDirectory, $"{deterministicHashCodeKey}{item.ImageFileHolder.ExtensionLowered}{_FileNameExtension}"));
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(mappingFromItem.Id, face.Location, ILocation.Digits, ILocation.Factor, face.OutputResolution);
fileInfo = new FileInfo(Path.Combine(facesDirectory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{_FileNameExtension}"));
if (!fileInfo.Exists)
{
if (fileInfo.Directory?.Parent is null)
@ -358,7 +346,7 @@ public class D_Face
if (File.Exists(parentCheck))
File.Delete(parentCheck);
}
collection.Add(new(face, fileInfo, Path.Combine(facesDirectory, $"{deterministicHashCodeKey}{item.ImageFileHolder.ExtensionLowered}{_HiddenFileNameExtension}")));
collection.Add(new(face, fileInfo, Path.Combine(facesDirectory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{_HiddenFileNameExtension}")));
if (_OverrideForFaceImages)
check = true;
else if (!fileInfo.Exists)
@ -367,7 +355,7 @@ public class D_Face
check = true;
}
if (check)
SaveFaces(item.ResizedFileHolder, collection);
SaveFaces(mappingFromItem.ResizedFileHolder, collection);
}
}

View File

@ -348,7 +348,22 @@ public partial class DlibDotNet
return result;
}
private void FullParallelForWork(A_Property propertyLogic, string[] mappedFaceFiles, string outputResolution, string bResultsFullGroupDirectory, string cResultsFullGroupDirectory, string dResultsFullGroupDirectory, string eDistanceContentDirectory, List<Tuple<string, DateTime>> sourceDirectoryChanges, List<FileHolder?> propertyFileHolderCollection, List<Shared.Models.Property?> propertyCollection, List<List<KeyValuePair<string, string>>> metadataCollections, List<Dictionary<string, int[]>> resizeKeyValuePairs, List<List<Shared.Models.Face>?> imageFaceCollections, Container container, int index, Item item)
private static MappingFromItem GetMappingFromItem(Item item)
{
MappingFromItem result;
bool? isWrongYear;
DateTime minimumDateTime;
if (item.Property?.Id is null)
throw new NotSupportedException();
if (item.Property?.Id is null || item.ImageFileHolder is null || item.ResizedFileHolder is null)
throw new NotSupportedException();
minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property);
(isWrongYear, _) = item.Property.IsWrongYear(item.ImageFileHolder.FullName, minimumDateTime);
result = new(item.Property.Id.Value, item.ImageFileHolder, isWrongYear, minimumDateTime, item.RelativePath, item.ResizedFileHolder);
return result;
}
private void FullParallelForWork(A_Property propertyLogic, Dictionary<int, List<(string, int)>> idToMappedFaceFilesCollection, string outputResolution, string bResultsFullGroupDirectory, string cResultsFullGroupDirectory, string dResultsFullGroupDirectory, string eDistanceContentDirectory, List<Tuple<string, DateTime>> sourceDirectoryChanges, List<FileHolder?> propertyFileHolderCollection, List<Shared.Models.Property?> propertyCollection, List<List<KeyValuePair<string, string>>> metadataCollections, List<Dictionary<string, int[]>> resizeKeyValuePairs, List<List<Shared.Models.Face>?> imageFaceCollections, Container container, int index, Item item)
{
if (item.ImageFileHolder is null)
throw new NullReferenceException(nameof(item.ImageFileHolder));
@ -378,22 +393,10 @@ public partial class DlibDotNet
sourceDirectoryChanges.Add(new Tuple<string, DateTime>(nameof(A_Property), (from l in subFileTuples select l.Item2).Max()));
}
}
(int metadataGroups, metadataCollection) = _Metadata.GetMetadataCollection(
_Configuration.PropertyConfiguration,
bResultsFullGroupDirectory,
subFileTuples,
parseExceptions,
item);
(int metadataGroups, metadataCollection) = _Metadata.GetMetadataCollection(_Configuration.PropertyConfiguration, bResultsFullGroupDirectory, subFileTuples, parseExceptions, item);
if (_AppSettings.MaxDegreeOfParallelism < 2)
ticks = LogDelta(ticks, nameof(B_Metadata.GetMetadataCollection));
imageResizeKeyValuePairs = _Resize.GetResizeKeyValuePairs(
_Configuration.PropertyConfiguration,
cResultsFullGroupDirectory,
subFileTuples,
parseExceptions,
original,
metadataCollection,
item);
imageResizeKeyValuePairs = _Resize.GetResizeKeyValuePairs(_Configuration.PropertyConfiguration, cResultsFullGroupDirectory, subFileTuples, parseExceptions, original, metadataCollection, item);
if (_AppSettings.MaxDegreeOfParallelism < 2)
ticks = LogDelta(ticks, nameof(C_Resize.GetResizeKeyValuePairs));
if (_Configuration.SaveResizedSubfiles)
@ -414,17 +417,21 @@ public partial class DlibDotNet
faces = null;
else
{
MappingFromItem mappingFromItem = GetMappingFromItem(item);
int[] outputResolutionCollection = imageResizeKeyValuePairs[outputResolution];
int outputResolutionWidth = outputResolutionCollection[0];
int outputResolutionHeight = outputResolutionCollection[1];
int outputResolutionOrientation = outputResolutionCollection[2];
faces = _Faces.GetFaces(dResultsFullGroupDirectory, subFileTuples, parseExceptions, item, property, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation);
faces = _Faces.GetFaces(dResultsFullGroupDirectory, subFileTuples, parseExceptions, property, mappingFromItem, outputResolutionWidth, outputResolutionHeight, outputResolutionOrientation);
if (_AppSettings.MaxDegreeOfParallelism < 2)
ticks = LogDelta(ticks, nameof(D_Face.GetFaces));
_Faces.SaveFaces(dResultsFullGroupDirectory, subFileTuples, parseExceptions, item, faces);
_Faces.SaveFaces(dResultsFullGroupDirectory, subFileTuples, parseExceptions, mappingFromItem, faces);
if (_AppSettings.MaxDegreeOfParallelism < 2)
ticks = LogDelta(ticks, nameof(D_Face.SaveFaces));
_ = _Distance.GetUnableToMatchCountAndRenameMatches(_Faces.FileNameExtension, eDistanceContentDirectory, item, faces, mappedFaceFiles);
if (item.Property?.Id is not null
&& faces.Any(l => l.FaceEncoding is not null && l.Location is not null && l.OutputResolution is not null)
&& idToMappedFaceFilesCollection.TryGetValue(item.Property.Id.Value, out List<(string, int)>? collection))
_ = _Distance.GetUnableToMatchCountAndRenameMatches(_Faces.FileNameExtension, eDistanceContentDirectory, mappingFromItem, faces, collection);
if (_Configuration.SaveFaceLandmarkForOutputResolutions.Contains(outputResolution))
{
throw new NotImplementedException();
@ -449,7 +456,7 @@ public partial class DlibDotNet
private int FullParallelWork(int maxDegreeOfParallelism,
A_Property propertyLogic,
string[] mappedFaceFiles,
Dictionary<int, List<(string, int)>> idToMappedFaceFilesCollection,
string outputResolution,
string bResultsFullGroupDirectory,
string cResultsFullGroupDirectory,
@ -491,7 +498,7 @@ public partial class DlibDotNet
{
FullParallelForWork(
propertyLogic,
mappedFaceFiles,
idToMappedFaceFilesCollection,
outputResolution,
bResultsFullGroupDirectory,
cResultsFullGroupDirectory,
@ -555,15 +562,7 @@ public partial class DlibDotNet
}
}
private void WriteGroup(
A_Property propertyLogic,
Shared.Models.Property[] propertyCollection,
List<List<KeyValuePair<string, string>>> metadataCollection,
List<Dictionary<string, int[]>> resizeKeyValuePairs,
List<List<Shared.Models.Face>?> imageFaceCollections,
string outputResolution,
Container container,
Item[] filteredItems)
private void WriteGroup(A_Property propertyLogic, Shared.Models.Property[] propertyCollection, List<List<KeyValuePair<string, string>>> metadataCollection, List<Dictionary<string, int[]>> resizeKeyValuePairs, List<List<Shared.Models.Face>?> imageFaceCollections, string outputResolution, Container container, Item[] filteredItems)
{
Item item;
string key;
@ -686,14 +685,7 @@ public partial class DlibDotNet
return new(aResultsFullGroupDirectory, bResultsFullGroupDirectory, cResultsFullGroupDirectory, dResultsFullGroupDirectory);
}
private void SetAngleBracketCollections(
A_Property propertyLogic,
string outputResolution,
Container container,
string aResultsFullGroupDirectory,
string bResultsFullGroupDirectory,
string cResultsFullGroupDirectory,
string dResultsFullGroupDirectory)
private void SetAngleBracketCollections(A_Property propertyLogic, string outputResolution, Container container, string aResultsFullGroupDirectory, string bResultsFullGroupDirectory, string cResultsFullGroupDirectory, string dResultsFullGroupDirectory)
{
_Faces.AngleBracketCollection.Clear();
_Resize.AngleBracketCollection.Clear();
@ -748,7 +740,7 @@ public partial class DlibDotNet
return results.ToArray();
}
private void FullDoWork(string argZero, Model? model, PredictorModel? predictorModel, string propertyRoot, long ticks, A_Property propertyLogic, int t, Container[] containers, string eDistanceContentDirectory, string[] mappedFaceFiles)
private void FullDoWork(string argZero, Model? model, PredictorModel? predictorModel, string propertyRoot, long ticks, A_Property propertyLogic, int t, Container[] containers, string eDistanceContentDirectory, Dictionary<int, List<(string, int)>> idToMappedFaceFilesCollection)
{
if (_Log is null)
throw new NullReferenceException(nameof(_Log));
@ -799,7 +791,7 @@ public partial class DlibDotNet
exceptionCount = FullParallelWork(
maxDegreeOfParallelism,
propertyLogic,
mappedFaceFiles,
idToMappedFaceFilesCollection,
outputResolution,
bResultsFullGroupDirectory,
cResultsFullGroupDirectory,
@ -875,17 +867,17 @@ public partial class DlibDotNet
{
if (item.Property?.Id is null || item.ImageFileHolder is null || item.ResizedFileHolder is null)
continue;
if (!item.Faces.Any())
if (!item.Faces.Any(l => l.FaceEncoding is not null && l.Location is not null && l.OutputResolution is not null))
continue;
minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property);
(isWrongYear, _) = item.Property.IsWrongYear(item.ImageFileHolder.FullName, minimumDateTime);
mappingFromItem = new(item.Property.Id.Value, item.ImageFileHolder, isWrongYear, minimumDateTime, item.RelativePath, item.ResizedFileHolder);
foreach (Shared.Models.Face face in item.Faces)
{
if (face.RelativePath != item.RelativePath)
break;
if (face.FaceEncoding is null || face.Location is null || face.OutputResolution is null)
continue;
minimumDateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property);
(isWrongYear, _) = item.Property.IsWrongYear(item.ImageFileHolder.FullName, minimumDateTime);
mappingFromItem = new(item.Property.Id.Value, item.ImageFileHolder, isWrongYear, minimumDateTime, item.ResizedFileHolder);
mappingFromPerson = new(approximateYears: null, by: null, displayDirectoryName: string.Empty, personBirthday: null, segmentB: string.Empty);
normalizedPixelPercentage = Shared.Models.Stateless.Methods.ILocation.GetNormalizedPixelPercentage(face.Location, Shared.Models.Stateless.ILocation.Digits, Shared.Models.Stateless.ILocation.Factor, face.OutputResolution);
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(item.Property.Id.Value, face.Location, Shared.Models.Stateless.ILocation.Digits, Shared.Models.Stateless.ILocation.Factor, face.OutputResolution);
@ -899,14 +891,10 @@ public partial class DlibDotNet
return results;
}
private void DistanceThenMapLogic(
string argZero,
long ticks,
PersonContainer[] personContainers,
Container[] containers,
string dResultsFullGroupDirectory,
string outputResolution)
private void DistanceThenMapLogic(string argZero, long ticks, PersonContainer[] personContainers, Container[] containers, string dResultsFullGroupDirectory, string outputResolution)
{
int? useFiltersCounter = null;
SortingContainer[] sortingContainers;
string dFacesContentDirectory = Path.Combine(dResultsFullGroupDirectory, "()");
List<Shared.Models.Face> distinctFilteredFaces = SetMappingThenGetDistinctFilteredFacesWithMapping(argZero, containers);
Shared.Models.Face[] selectedFilteredFaces = E_Distance.GetSelectedFilteredFaces(distinctFilteredFaces);
@ -927,20 +915,20 @@ public partial class DlibDotNet
eDistanceContentDirectory,
distinctFilteredFaces,
_Distance);
SortingContainer[] sortingContainers = _Distance.SetFaceMappingSortingCollectionThenGetSortingContainers(
_AppSettings.MaxDegreeOfParallelism,
ticks,
mapLogic,
selectedFilteredFaces);
sortingContainers = _Distance.SetFaceMappingSortingCollectionThenGetSortingContainers(_AppSettings.MaxDegreeOfParallelism, ticks, mapLogic, selectedFilteredFaces, useFiltersCounter);
if (!sortingContainers.Any())
{
for (useFiltersCounter = 1; useFiltersCounter < 11; useFiltersCounter++)
{
sortingContainers = _Distance.SetFaceMappingSortingCollectionThenGetSortingContainers(_AppSettings.MaxDegreeOfParallelism, ticks, mapLogic, selectedFilteredFaces, useFiltersCounter);
if (sortingContainers.Any())
break;
}
}
E_Distance.SaveFaceDistances(_Configuration.PropertyConfiguration, sortingContainers);
int totalNotMapped = mapLogic.AddToMapping(distinctFilteredFaces);
if (totalNotMapped > 0)
mapLogic.ForceSingleImageThenSaveMapping(
dFacesContentDirectory,
d2FacePartsContentDirectory,
distinctFilteredFaces,
sortingContainers,
totalNotMapped);
mapLogic.ForceSingleImageThenSaveMapping(dFacesContentDirectory, d2FacePartsContentDirectory, distinctFilteredFaces, sortingContainers, useFiltersCounter, totalNotMapped);
mapLogic.CopyManualFiles(dFacesContentDirectory, distinctFilteredFaces);
if (_MapConfiguration.MappingSaveNotMapped)
mapLogic.SaveNotMappedTicks();
@ -1025,12 +1013,7 @@ public partial class DlibDotNet
string cResultsFullGroupDirectory;
string dResultsFullGroupDirectory;
string eDistanceContentDirectory = Property.Models.Stateless.IResult.GetResultsDateGroupDirectory(_Configuration.PropertyConfiguration, nameof(E_Distance), "()");
string[] mappedFaceFiles = Map.Models.Stateless.Methods.IMapLogic.DeleteEmptyDirectoriesAndGetMappedFaceFiles(
_MapConfiguration,
_Faces.FileNameExtension,
ticks,
eDistanceContentDirectory,
personContainers);
Dictionary<int, List<(string, int)>> idToMappedFaceFilesCollection = Map.Models.Stateless.Methods.IMapLogic.DeleteEmptyDirectoriesAndGetMappedFaceFiles(_MapConfiguration, _Faces.FileNameExtension, ticks, eDistanceContentDirectory, personContainers);
int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - ticks).TotalSeconds);
string message = $") Building Container(s) - {totalSeconds} total second(s)";
A_Property propertyLogic = new(_AppSettings.MaxDegreeOfParallelism, _Configuration.PropertyConfiguration, _Resize.FileNameExtension, _Configuration.Reverse, model, predictorModel);
@ -1055,15 +1038,9 @@ public partial class DlibDotNet
_Configuration.PropertyConfiguration,
nameof(A_Property),
create: false);
propertyLogic = new(
_AppSettings.MaxDegreeOfParallelism,
_Configuration.PropertyConfiguration,
_Resize.FileNameExtension,
_Configuration.Reverse,
model,
predictorModel);
propertyLogic = new(_AppSettings.MaxDegreeOfParallelism, _Configuration.PropertyConfiguration, _Resize.FileNameExtension, _Configuration.Reverse, model, predictorModel);
}
FullDoWork(argZero, model, predictorModel, propertyRoot, ticks, propertyLogic, t, containers, eDistanceContentDirectory, mappedFaceFiles);
FullDoWork(argZero, model, predictorModel, propertyRoot, ticks, propertyLogic, t, containers, eDistanceContentDirectory, idToMappedFaceFilesCollection);
foreach (string outputResolution in _Configuration.OutputResolutions)
{
if (_FirstRun || container is not null)

View File

@ -127,7 +127,27 @@ public class MapLogic
return results;
}
public List<Sorting> GetSortingCollection(int i, FaceDistance faceDistanceEncoding, List<FaceDistance> faceDistanceLengths, bool anyLowerThanTolerance)
public bool Used(FaceDistance faceDistanceEncoding)
{
bool result = false;
if (faceDistanceEncoding.NormalizedPixelPercentage is null)
throw new NotSupportedException();
List<int>? normalizedPixelPercentages;
Dictionary<int, PersonContainer[]>? normalizedPixelPercentageToPersonContainers;
if (_SkipCollection.TryGetValue(faceDistanceEncoding.Id, out normalizedPixelPercentages))
{
if (normalizedPixelPercentages.Contains(faceDistanceEncoding.NormalizedPixelPercentage.Value))
result = true;
}
if (!result && _IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(faceDistanceEncoding.Id, out normalizedPixelPercentageToPersonContainers))
{
if (normalizedPixelPercentageToPersonContainers.ContainsKey(faceDistanceEncoding.NormalizedPixelPercentage.Value))
result = true;
}
return result;
}
public List<Sorting> GetSortingCollection(int i, FaceDistance faceDistanceEncoding, List<FaceDistance> faceDistanceLengths)
{
if (_Configuration is null)
throw new NullReferenceException(nameof(_Configuration));
@ -135,33 +155,35 @@ public class MapLogic
Sorting sorting;
FaceDistance faceDistanceLength;
List<int>? normalizedPixelPercentages;
Dictionary<int, PersonContainer[]>? keyValuePairs;
Dictionary<int, PersonContainer[]>? normalizedPixelPercentageToPersonContainers;
List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection;
for (int j = 0; j < faceDistanceLengths.Count; j++)
{
if (j == i)
continue;
faceDistanceLength = faceDistanceLengths[j];
if (faceDistanceEncoding.NormalizedPixelPercentage is null || faceDistanceLength.NormalizedPixelPercentage is null || faceDistanceLength.Length is null)
if (faceDistanceEncoding.NormalizedPixelPercentage is null)
throw new NotSupportedException();
if (faceDistanceLength.Length == 0)
if (j == i)
continue;
if (_SkipCollection.TryGetValue(faceDistanceEncoding.Id, out normalizedPixelPercentages))
{
if (normalizedPixelPercentages.Contains(faceDistanceEncoding.NormalizedPixelPercentage.Value))
continue;
}
if (_IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(faceDistanceEncoding.Id, out keyValuePairs))
if (_IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(faceDistanceEncoding.Id, out normalizedPixelPercentageToPersonContainers))
{
if (keyValuePairs.ContainsKey(faceDistanceEncoding.NormalizedPixelPercentage.Value))
if (normalizedPixelPercentageToPersonContainers.ContainsKey(faceDistanceEncoding.NormalizedPixelPercentage.Value))
continue;
}
if (!_IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(faceDistanceLength.Id, out keyValuePairs))
faceDistanceLength = faceDistanceLengths[j];
if (faceDistanceLength.NormalizedPixelPercentage is null || faceDistanceLength.Length is null)
throw new NotSupportedException();
if (faceDistanceLength.Length == 0)
continue;
if (!keyValuePairs.ContainsKey(faceDistanceLength.NormalizedPixelPercentage.Value))
if (!_IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(faceDistanceLength.Id, out normalizedPixelPercentageToPersonContainers))
continue;
personKeysRangesCollection = GetPersonKeysRangesCollection(keyValuePairs[faceDistanceLength.NormalizedPixelPercentage.Value]);
sorting = ISorting.Get(_Configuration.FaceDistancePermyriad, _Configuration.FaceDistanceTolerance, faceDistanceEncoding, faceDistanceLength, anyLowerThanTolerance, personKeysRangesCollection);
if (!normalizedPixelPercentageToPersonContainers.ContainsKey(faceDistanceLength.NormalizedPixelPercentage.Value))
continue;
personKeysRangesCollection = GetPersonKeysRangesCollection(normalizedPixelPercentageToPersonContainers[faceDistanceLength.NormalizedPixelPercentage.Value]);
sorting = ISorting.Get(_Configuration.FaceDistancePermyriad, _Configuration.FaceDistanceTolerance, faceDistanceEncoding, faceDistanceLength, personKeysRangesCollection);
if (sorting.DistancePermyriad == 0)
continue;
if (sorting.Id == faceDistanceEncoding.Id)
@ -299,14 +321,14 @@ public class MapLogic
return result;
}
private void SaveContainers(List<SaveContainer> saveContainers)
private void SaveContainers(int totalNotMapped, int updated, List<SaveContainer> saveContainers)
{
string checkFile;
string sourceFile;
WindowsShortcut windowsShortcut;
string[] directories = (from l in saveContainers select l.Directory).Distinct().ToArray();
int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - _Ticks).TotalSeconds);
string message = $") {saveContainers.Count:000} save(s) - {totalSeconds} total second(s)";
string message = $") {saveContainers.Count:000} save(s) - {totalNotMapped} Total not Mapped - {updated} Updated - {totalSeconds} total second(s)";
ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true };
foreach (string directory in directories)
{
@ -379,8 +401,10 @@ public class MapLogic
{
if (_Configuration is null)
throw new NullReferenceException(nameof(_Configuration));
int updated = 0;
string directory;
const int zero = 0;
int totalNotMapped = 0;
string personKeyFormatted;
SaveContainer saveContainer;
PersonBirthday personBirthday;
@ -396,7 +420,7 @@ public class MapLogic
saveContainer = new(directory);
saveContainers.Add(saveContainer);
}
SaveContainers(saveContainers);
SaveContainers(totalNotMapped, updated, saveContainers);
}
public List<(Face, long?, (string, string, string, string))> GetCollection(List<Face> distinctFilteredFaces)
@ -485,41 +509,37 @@ public class MapLogic
if (_Configuration is null)
throw new NullReferenceException(nameof(_Configuration));
int result = 0;
Dictionary<int, HashSet<int>> results = new();
string key;
const int zero = 0;
HashSet<int> hashSet;
string mappingSegmentB;
string personKeyFormatted;
List<Mapping> checkCollection;
PersonBirthday personBirthday;
PersonContainer[] personContainers;
const int by = Stateless.IMapLogic.Sorting;
Dictionary<int, PersonContainer[]>? keyValuePairs;
List<int> normalizedPixelPercentageCollection;
Dictionary<string, List<Mapping>> checkKeyValuePairs = new();
Dictionary<int, List<int>> idToNormalizedPixelPercentageCollection = new();
Dictionary<int, PersonContainer[]>? normalizedPixelPercentageToPersonContainers;
int totalSeconds = (int)Math.Floor(new TimeSpan(DateTime.Now.Ticks - _Ticks).TotalSeconds);
string message = $") {sortingContainers.Length:000} Update From Sorting Container(s) - {totalSeconds} total second(s)";
ProgressBarOptions options = new() { ProgressCharacter = '─', ProgressBarOnBottom = true, DisableBottomPercentage = true };
foreach (KeyValuePair<int, Dictionary<int, PersonContainer[]>> keyValuePair in _IdThenNormalizedPixelPercentageToPersonContainers)
results.Add(keyValuePair.Key, (from l in keyValuePair.Value select l.Key).ToHashSet());
using ProgressBar progressBar = new(sortingContainers.Length, message, options);
foreach (SortingContainer sortingContainer in sortingContainers)
{
progressBar.Tick();
if (sortingContainer.Face.Mapping is null)
throw new NotSupportedException();
if (!_IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(sortingContainer.Sorting.Id, out keyValuePairs))
if (!_IdThenNormalizedPixelPercentageToPersonContainers.TryGetValue(sortingContainer.Sorting.Id, out normalizedPixelPercentageToPersonContainers))
throw new NotSupportedException();
if (!results.ContainsKey(sortingContainer.Face.Mapping.MappingFromItem.Id))
results.Add(sortingContainer.Face.Mapping.MappingFromItem.Id, new());
hashSet = results[sortingContainer.Face.Mapping.MappingFromItem.Id];
if (hashSet.Contains(sortingContainer.Face.Mapping.MappingFromLocation.NormalizedPixelPercentage))
continue;
if (!keyValuePairs.ContainsKey(sortingContainer.Sorting.NormalizedPixelPercentage))
if (!normalizedPixelPercentageToPersonContainers.ContainsKey(sortingContainer.Sorting.NormalizedPixelPercentage))
throw new NotSupportedException();
personContainers = keyValuePairs[sortingContainer.Sorting.NormalizedPixelPercentage];
if (sortingContainer.Face.Mapping.MappingFromLocation.Confidence < _Configuration.FaceDistanceMinimumConfidence || sortingContainer.Sorting.DistancePermyriad > _Configuration.FaceDistancePermyriad || sortingContainer.Sorting.DaysDelta > _Configuration.SortingDaysDeltaTolerance)
if (!idToNormalizedPixelPercentageCollection.ContainsKey(sortingContainer.Face.Mapping.MappingFromItem.Id))
idToNormalizedPixelPercentageCollection.Add(sortingContainer.Face.Mapping.MappingFromItem.Id, new());
normalizedPixelPercentageCollection = idToNormalizedPixelPercentageCollection[sortingContainer.Face.Mapping.MappingFromItem.Id];
if (normalizedPixelPercentageCollection.Contains(sortingContainer.Face.Mapping.MappingFromLocation.NormalizedPixelPercentage))
continue;
personContainers = normalizedPixelPercentageToPersonContainers[sortingContainer.Sorting.NormalizedPixelPercentage];
foreach (PersonContainer personContainer in personContainers)
{
if (personContainer.Key is null || personContainer.Birthdays is null || !personContainer.Birthdays.Any())
@ -533,7 +553,7 @@ public class MapLogic
checkCollection = checkKeyValuePairs[key];
if (checkCollection.Count > _Configuration.SortingMaximumPerKey)
continue;
_ = hashSet.Add(sortingContainer.Sorting.NormalizedPixelPercentage);
normalizedPixelPercentageCollection.Add(sortingContainer.Face.Mapping.MappingFromLocation.NormalizedPixelPercentage);
sortingContainer.Face.Mapping.UpdateMappingFromPerson(personContainer.ApproximateYears, by, personContainer.DisplayDirectoryName, personBirthday, mappingSegmentB);
checkCollection.Add(sortingContainer.Face.Mapping);
result += 1;
@ -578,7 +598,7 @@ public class MapLogic
}
}
private List<SaveContainer> GetMappingSaveContainers(string dFacesContentDirectory, string d2FacePartsContentDirectory, List<Face> filteredFaces)
private List<SaveContainer> GetMappingSaveContainers(string dFacesContentDirectory, string d2FacePartsContentDirectory, List<Face> filteredFaces, int? useFiltersCounter)
{
if (_Configuration is null)
throw new NullReferenceException(nameof(_Configuration));
@ -612,6 +632,8 @@ public class MapLogic
personKeyFormatted = IPersonBirthday.GetFormatted(_Configuration.PersonBirthdayFormat, face.Mapping.MappingFromPerson.PersonBirthday);
if (face.Mapping.MappingFromPerson.By is null)
by = $"{nameof(Stateless.IMapLogic.Mapping)}Null";
else if (useFiltersCounter.HasValue && face.Mapping.MappingFromPerson.By.Value == Stateless.IMapLogic.Sorting)
by = $"{nameof(Stateless.IMapLogic.Sorting)} Modified Filters - {useFiltersCounter.Value}";
else
{
if (face.Mapping.MappingFromPerson.By == Stateless.IMapLogic.Mapping && !_Configuration.MappingSaveMapped)
@ -650,22 +672,97 @@ public class MapLogic
return results;
}
public void ForceSingleImageThenSaveMapping(string dFacesContentDirectory, string d2FacePartsContentDirectory, List<Face> distinctFilteredFaces, SortingContainer[] sortingContainers, int totalNotMapped)
private static IEnumerable<(string, string)> GetCollection(string[] yearDirectories)
{
foreach (string l in yearDirectories)
yield return new(l, Path.GetFileName(l));
}
private static void SaveMappingShortcuts(string mappingDirectory)
{
string? shortcutFileName;
string[] yearDirectories;
string personKeyFormatted;
string[] personNameDirectories;
WindowsShortcut windowsShortcut;
string personDisplayDirectoryName;
(string, string)[] yearDirectoryNameCheck;
List<(string, string)> yearDirectoryNames = new();
string[] personKeyDirectories = Directory.GetDirectories(mappingDirectory, "*", SearchOption.TopDirectoryOnly);
foreach (string personKeyDirectory in personKeyDirectories)
{
windowsShortcut = new();
shortcutFileName = null;
yearDirectoryNames.Clear();
personKeyFormatted = Path.GetFileName(personKeyDirectory);
yearDirectories = Directory.GetDirectories(personKeyDirectory, "*", SearchOption.TopDirectoryOnly);
yearDirectoryNames.AddRange(GetCollection(yearDirectories));
yearDirectoryNameCheck = (from l in yearDirectoryNames where l.Item2.Contains('^') select l).OrderByDescending(l => l.Item2).ToArray();
if (!yearDirectoryNameCheck.Any())
yearDirectoryNameCheck = (from l in yearDirectoryNames where l.Item2.Contains('~') select l).OrderByDescending(l => l.Item2).ToArray();
if (!yearDirectoryNameCheck.Any())
yearDirectoryNameCheck = (from l in yearDirectoryNames where l.Item2.Contains('=') select l).OrderByDescending(l => l.Item2).ToArray();
if (!yearDirectoryNameCheck.Any())
yearDirectoryNameCheck = (from l in yearDirectoryNames select l).OrderByDescending(l => l).ToArray();
if (!yearDirectoryNameCheck.Any())
continue;
foreach ((string yearDirectory, string yearDirectoryName) in yearDirectoryNameCheck)
{
personNameDirectories = Directory.GetDirectories(yearDirectory, "*", SearchOption.TopDirectoryOnly);
foreach (string personNameDirectory in personNameDirectories)
{
personDisplayDirectoryName = Path.GetFileName(personNameDirectory).Split('-')[0];
if (personDisplayDirectoryName is null)
continue;
windowsShortcut.Path = yearDirectory;
windowsShortcut.Description = yearDirectoryName;
shortcutFileName = Path.Combine(mappingDirectory, $"{personDisplayDirectoryName} [{windowsShortcut.Description}].lnk");
break;
}
if (shortcutFileName is not null)
{
if (!File.Exists(shortcutFileName))
break;
}
}
if (shortcutFileName is null || windowsShortcut.Path is null || windowsShortcut.Description is null)
continue;
try
{
windowsShortcut.Save(shortcutFileName);
windowsShortcut.Dispose();
}
catch (Exception)
{ }
}
}
public void ForceSingleImageThenSaveMapping(string dFacesContentDirectory, string d2FacePartsContentDirectory, List<Face> distinctFilteredFaces, SortingContainer[] sortingContainers, int? useFiltersCounter, int totalNotMapped)
{
if (_Configuration is null)
throw new NullReferenceException(nameof(_Configuration));
int updated;
List<SaveContainer> saveContainers;
if (!sortingContainers.Any())
{
updated = 0;
ForceSingleImage(distinctFilteredFaces);
saveContainers = GetMappingSaveContainers(dFacesContentDirectory, d2FacePartsContentDirectory, distinctFilteredFaces);
saveContainers = GetMappingSaveContainers(dFacesContentDirectory, d2FacePartsContentDirectory, distinctFilteredFaces, useFiltersCounter);
}
else
{
int updated = UpdateFromSortingContainers(sortingContainers);
if (totalNotMapped - updated > 0)
updated = UpdateFromSortingContainers(sortingContainers);
if (useFiltersCounter is null && totalNotMapped - updated > 0)
ForceSingleImage(distinctFilteredFaces);
saveContainers = GetMappingSaveContainers(dFacesContentDirectory, d2FacePartsContentDirectory, distinctFilteredFaces);
saveContainers = GetMappingSaveContainers(dFacesContentDirectory, d2FacePartsContentDirectory, distinctFilteredFaces, useFiltersCounter);
}
SaveContainers(totalNotMapped, updated, saveContainers);
if (_Configuration.MappingSaveMapped)
{
string mappingDirectory = Path.Combine(_EDistanceContentTicksDirectory, nameof(Stateless.IMapLogic.Mapping));
if (Directory.Exists(mappingDirectory))
SaveMappingShortcuts(mappingDirectory);
}
SaveContainers(saveContainers);
}
private static Dictionary<int, Dictionary<int, Face>> GetKeyValuePairs(List<Face> distinctFilteredFaces)

View File

@ -177,9 +177,26 @@ internal abstract class MapLogic
return results;
}
internal static string[] DeleteEmptyDirectoriesAndGetMappedFaceFiles(Configuration configuration, string facesFileNameExtension, long ticks, string eDistanceContentDirectory, PersonContainer[] personContainers)
public static Dictionary<int, List<(string, int)>> GetIdToCollection(string facesFileNameExtension, List<(string, string[], string)> collection)
{
string[] results;
Dictionary<int, List<(string, int)>> results = new();
int? id;
int? normalizedPixelPercentage;
foreach ((string personKeyFormatted, string[] personDisplayDirectoryNames, string mappedFaceFile) in collection)
{
(id, normalizedPixelPercentage, _) = IMapping.GetReversedDeterministicHashCodeKey(facesFileNameExtension, mappedFaceFile);
if (id is null || normalizedPixelPercentage is null)
continue;
if (!results.ContainsKey(id.Value))
results.Add(id.Value, new());
results[id.Value].Add(new(mappedFaceFile, normalizedPixelPercentage.Value));
}
return results;
}
internal static Dictionary<int, List<(string, int)>> DeleteEmptyDirectoriesAndGetMappedFaceFiles(Configuration configuration, string facesFileNameExtension, long ticks, string eDistanceContentDirectory, PersonContainer[] personContainers)
{
Dictionary<int, List<(string, int)>> results;
string personKeyFormatted;
List<string> personKeyFormattedCollection = new();
_ = GetDistinctCollection(configuration, personContainers.ToList(), new());
@ -196,13 +213,13 @@ internal abstract class MapLogic
personKeyFormattedCollection.Add(personKeyFormatted);
}
}
List<(string PersonKeyFormatted, string[] PersonDisplayDirectoryNames, string File)> collection = DeleteEmptyDirectoriesAndGetCollection(
List<(string, string[], string)> collection = DeleteEmptyDirectoriesAndGetCollection(
configuration,
facesFileNameExtension,
personKeyFormattedCollection,
ticksDirectories,
message);
results = (from l in collection select l.File).ToArray();
results = GetIdToCollection(facesFileNameExtension, collection);
return results;
}

View File

@ -3,9 +3,9 @@ namespace View_by_Distance.Map.Models.Stateless.Methods;
public interface IMapLogic
{ // ...
string[] TestStatic_DeleteEmptyDirectoriesAndGetMappedFaceFiles(Configuration configuration, string facesFileNameExtension, long ticks, string eDistanceContentDirectory, Shared.Models.PersonContainer[] personContainers) =>
Dictionary<int, List<(string, int)>> TestStatic_DeleteEmptyDirectoriesAndGetMappedFaceFiles(Configuration configuration, string facesFileNameExtension, long ticks, string eDistanceContentDirectory, Shared.Models.PersonContainer[] personContainers) =>
DeleteEmptyDirectoriesAndGetMappedFaceFiles(configuration, facesFileNameExtension, ticks, eDistanceContentDirectory, personContainers);
static string[] DeleteEmptyDirectoriesAndGetMappedFaceFiles(Configuration configuration, string facesFileNameExtension, long ticks, string eDistanceContentDirectory, Shared.Models.PersonContainer[] personContainers) =>
static Dictionary<int, List<(string, int)>> DeleteEmptyDirectoriesAndGetMappedFaceFiles(Configuration configuration, string facesFileNameExtension, long ticks, string eDistanceContentDirectory, Shared.Models.PersonContainer[] personContainers) =>
MapLogic.DeleteEmptyDirectoriesAndGetMappedFaceFiles(configuration, facesFileNameExtension, ticks, eDistanceContentDirectory, personContainers);
}

View File

@ -153,11 +153,9 @@ public class Container
Shared.Models.Container[] results;
Item item;
int length;
int itemCount;
int additional;
string inferred;
List<Item> items;
string[] existing;
string keyWithJson;
string relativePath;
FileHolder keyFileHolder;
@ -256,18 +254,8 @@ public class Container
}
else
{
additional = 0;
container = keyValuePairs[sourceDirectory];
itemCount = items.Count;
existing = (from l in container.Items select l.ImageFileHolder?.FullName).ToArray();
for (int i = 0; i < itemCount; i++)
{
item = items[i];
if (item.ImageFileHolder is null || existing.Contains(item.ImageFileHolder.FullName))
continue;
additional += 1;
items.Add(item);
}
(items, additional) = Shared.Models.Stateless.Methods.IItem.GetMerged(container.Items, items);
result += additional;
container = new(container.G, items, container.SourceDirectory);
keyValuePairs[sourceDirectory] = container;

View File

@ -66,12 +66,8 @@ public class Face : Properties.IFace
public void SetFaceParts(Dictionary<Stateless.FacePart, FacePoint[]> faceParts) => _FaceParts = faceParts;
public void ReleaseFaceDistance() => _FaceDistance = null;
public void SetMapping(Mapping mapping) => _Mapping = mapping;
public void SetFaceDistance(FaceDistance? faceDistance) => _FaceDistance = faceDistance;
public void ClearFaceDistance() => _FaceDistance = null;
}

View File

@ -10,15 +10,17 @@ public class MappingFromItem : Properties.IMappingFromItem
public FileHolder ImageFileHolder { init; get; }
public bool? IsWrongYear { init; get; }
public DateTime MinimumDateTime { init; get; }
public string RelativePath { init; get; }
public FileHolder ResizedFileHolder { init; get; }
[JsonConstructor]
public MappingFromItem(int id, FileHolder imageFileHolder, bool? isWrongYear, DateTime minimumDateTime, FileHolder resizedFileHolder)
public MappingFromItem(int id, FileHolder imageFileHolder, bool? isWrongYear, DateTime minimumDateTime, string relativePath, FileHolder resizedFileHolder)
{
Id = id;
ImageFileHolder = imageFileHolder;
IsWrongYear = isWrongYear;
MinimumDateTime = minimumDateTime;
RelativePath = relativePath;
ResizedFileHolder = resizedFileHolder;
}

View File

@ -7,6 +7,7 @@ public interface IMappingFromItem
public FileHolder ImageFileHolder { init; get; }
public bool? IsWrongYear { init; get; }
public DateTime MinimumDateTime { init; get; }
public string RelativePath { init; get; }
public FileHolder ResizedFileHolder { init; get; }
}

View File

@ -1,4 +1,3 @@
using System.Text.Json;
using System.Text.Json.Serialization;
namespace View_by_Distance.Shared.Models;
@ -18,7 +17,7 @@ public record class SortingContainer : Properties.ISortingContainer
public override string ToString()
{
string result = JsonSerializer.Serialize(this, new JsonSerializerOptions() { WriteIndented = true });
string result = string.Concat(Face.Mapping?.MappingFromItem.Id, '\t', Face.Mapping?.MappingFromLocation.NormalizedPixelPercentage, '\t', Sorting.Id, '\t', Sorting.NormalizedPixelPercentage, '\t', Sorting.Older, '\t', Sorting.WithinRange, '\t', Sorting.DistancePermyriad, '\t', Sorting.DaysDelta);
return result;
}

View File

@ -21,7 +21,7 @@ public interface IAge
char[] TestStatic_GetChars() =>
GetChars();
static char[] GetChars() =>
new char[] { '!', '^', '_', '~' };
new char[] { '!', '^', '_', '~', '+' };
int? TestStatic_GetApproximateYears(string personDisplayDirectoryName, char[] chars) =>
GetApproximateYears(personDisplayDirectoryName, chars);

View File

@ -3,7 +3,13 @@ namespace View_by_Distance.Shared.Models.Stateless.Methods;
public interface IItem
{ // ...
string TestStatic_GetWrongYearFlag(bool? isWrongYear);
string TestStatic_GetWrongYearFlag(bool? isWrongYear) =>
GetWrongYearFlag(isWrongYear);
static string GetWrongYearFlag(bool? isWrongYear) => isWrongYear is null ? "#" : isWrongYear.Value ? "~" : "=";
(List<Models.Item>, int) TestStatic_GetMerged(List<Models.Item> itemsA, List<Models.Item> itemsB) =>
GetMerged(itemsA, itemsB);
static (List<Models.Item>, int) GetMerged(List<Models.Item> itemsA, List<Models.Item> itemsB) =>
Item.GetMerged(itemsA, itemsB);
}

View File

@ -8,9 +8,9 @@ public interface ISorting
static Models.Sorting[] Sort(List<Models.Sorting> collection) =>
(from l in collection orderby l.WithinRange, l.DistancePermyriad, l.DaysDelta select l).ToArray();
Models.Sorting TestStatic_Get(int faceDistancePermyriad, double faceDistanceTolerance, Models.FaceDistance faceDistanceEncoding, Models.FaceDistance faceDistanceLength, bool anyLowerThanTolerance, List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection) =>
Get(faceDistancePermyriad, faceDistanceTolerance, faceDistanceEncoding, faceDistanceLength, anyLowerThanTolerance, personKeysRangesCollection);
static Models.Sorting Get(int faceDistancePermyriad, double faceDistanceTolerance, Models.FaceDistance faceDistanceEncoding, Models.FaceDistance faceDistanceLength, bool anyLowerThanTolerance, List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection) =>
Sorting.Get(faceDistancePermyriad, faceDistanceTolerance, faceDistanceEncoding, faceDistanceLength, anyLowerThanTolerance, personKeysRangesCollection);
Models.Sorting TestStatic_Get(int faceDistancePermyriad, double faceDistanceTolerance, Models.FaceDistance faceDistanceEncoding, Models.FaceDistance faceDistanceLength, List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection) =>
Get(faceDistancePermyriad, faceDistanceTolerance, faceDistanceEncoding, faceDistanceLength, personKeysRangesCollection);
static Models.Sorting Get(int faceDistancePermyriad, double faceDistanceTolerance, Models.FaceDistance faceDistanceEncoding, Models.FaceDistance faceDistanceLength, List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection) =>
Sorting.Get(faceDistancePermyriad, faceDistanceTolerance, faceDistanceEncoding, faceDistanceLength, personKeysRangesCollection);
}

View File

@ -3,6 +3,28 @@ namespace View_by_Distance.Shared.Models.Stateless.Methods;
internal abstract class Item
{
internal static double GetDefaultValue() => throw new Exception();
internal static (List<Models.Item>, int) GetMerged(List<Models.Item> itemsA, List<Models.Item> itemsB)
{
int result = 0;
List<Models.Item> results = new();
List<string> collection = new();
foreach (Models.Item item in itemsA)
{
if (item.ImageFileHolder is null)
continue;
results.Add(item);
collection.Add(item.ImageFileHolder.FullName);
}
foreach (Models.Item item in itemsB)
{
if (item.ImageFileHolder is null)
continue;
if (collection.Contains(item.ImageFileHolder.FullName))
continue;
result++;
results.Add(item);
}
return new(results, result);
}
}

View File

@ -3,45 +3,31 @@ namespace View_by_Distance.Shared.Models.Stateless.Methods;
internal abstract class Sorting
{
internal static Models.Sorting Get(int faceDistancePermyriad, double faceDistanceTolerance, Models.FaceDistance faceDistanceEncoding, Models.FaceDistance faceDistanceLength, bool anyLowerThanTolerance, List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection)
internal static Models.Sorting Get(int faceDistancePermyriad, double faceDistanceTolerance, Models.FaceDistance faceDistanceEncoding, Models.FaceDistance faceDistanceLength, List<(long lcl, long minimum, long maximum, long ucl)> personKeysRangesCollection)
{
Models.Sorting result;
if (faceDistanceLength.Length is null)
throw new NotSupportedException();
if (faceDistanceLength.NormalizedPixelPercentage is null)
throw new NotSupportedException();
bool older;
int daysDelta;
int withinRange;
int distancePermyriad;
if (faceDistanceLength.Length.Value == 0 || (anyLowerThanTolerance && faceDistanceLength.Length.Value >= faceDistanceTolerance))
if (faceDistanceEncoding.MinimumDateTime is null || faceDistanceLength.MinimumDateTime is null)
throw new NotSupportedException();
List<int> withinRanges = new();
long ticks = faceDistanceEncoding.MinimumDateTime.Value.Ticks;
TimeSpan timeSpan = new(faceDistanceLength.MinimumDateTime.Value.Ticks - ticks);
bool older = timeSpan.TotalMilliseconds < 0;
int daysDelta = (int)Math.Round(Math.Abs(timeSpan.TotalDays), 0);
int distancePermyriad = (int)(faceDistanceLength.Length.Value / faceDistanceTolerance * faceDistancePermyriad);
foreach ((long lcl, long minimum, long maximum, long ucl) in personKeysRangesCollection)
{
older = false;
daysDelta = 0;
withinRange = 0;
distancePermyriad = 0;
}
else
{
if (faceDistanceEncoding.MinimumDateTime is null || faceDistanceLength.MinimumDateTime is null)
throw new NotSupportedException();
List<int> withinRanges = new();
long ticks = faceDistanceEncoding.MinimumDateTime.Value.Ticks;
TimeSpan timeSpan = new(faceDistanceLength.MinimumDateTime.Value.Ticks - ticks);
older = timeSpan.TotalMilliseconds < 0;
daysDelta = (int)Math.Round(Math.Abs(timeSpan.TotalDays), 0);
distancePermyriad = (int)(faceDistanceLength.Length.Value / faceDistanceTolerance * faceDistancePermyriad);
foreach ((long lcl, long minimum, long maximum, long ucl) in personKeysRangesCollection)
{
if (ticks > minimum && ticks < maximum)
withinRanges.Add(0);
else if (ticks > lcl && ticks < ucl)
withinRanges.Add(1);
else
withinRanges.Add(2);
}
withinRange = withinRanges.Max();
if (ticks > minimum && ticks < maximum)
withinRanges.Add(0);
else if (ticks > lcl && ticks < ucl)
withinRanges.Add(1);
else
withinRanges.Add(2);
}
int withinRange = withinRanges.Max();
result = new(daysDelta, distancePermyriad, faceDistanceLength.Id, faceDistanceLength.NormalizedPixelPercentage.Value, older, withinRange);
return result;
}