I have 3 people living in 3 houses.
I have a button with which I make an assignment for certain persons. It becomes a kind of user administration. E.g. person A has the permission to enter house C.
I would like to be able to display only the houses that have not been assigned yet.
Illustrated as follows:
If I want to assign him a new role now (caretaker of house C), I want only house C (the only unassigned house) to be displayed in the dropdown list.
Problem: Currently all houses are displayed.
Code structure:
I can create a new person or edit an existing person. I have an enum class for role assignment:
public enum RoleType
{
[Display(Name = "Owner")]
Owner = 0,
[Display(Name = "Janitor")]
Janitor = 1
}
I also have a model for role definition:
public class RoleDefinitionModel
{
private RoleType? _role;
private House _selectedHouse;
public RoleDefinitionModel(IList<House> availableHouse, RoleType? selectedRole, House selectedHouse)
{
AvailableHouses = availableHouse;
_role = selectedRole;
_selectedHouse = selectedHouse;
StartChangeTracking();
}
public virtual RoleType? SelectedRole
{
get { return _role; }
set
{
if (_role == value)
return;
_role = value;
NotifyChanges();
}
}
public virtual House SelectedHouse
{
get { return _selectedHouse; }
set
{
if (_selectedHouse == value)
return;
_selectedHouse = value;
NotifyChanges();
}
}
public virtual IList<House> AvailableHouses { get; }
public virtual IList<RoleType> AvailableRoles { get; } = Enum<RoleType>.GetValues().ToList();
}
I already have an add and remove method, which also work. There is only one problem: When I click on the button I get my desired dropdown. But I can select all houses. And I only want to see the houses to which I have not been assigned a role yet.
public virtual void AddRoleDefinition()
{
var roleDefinition = new RoleDefinitionModel(House, null, null);
_roleDefinitions.Add(roleDefinition);
this.SubscribeChanged(roleDefinition);
}
Which is the most effective way to check it:
Where()
and Any()
from System.Linq:_roleDefinitions.Where(....Any());
Contains()
or Remove()
in a foreach-loop?
for (var i = selectedHouse.Count - 1; i >= 0; --i)
{
if (availableHouses.Contains(selectedHouse[i].Uid))
{
availableHouses.Remove(selectedHouse[i]);
}
}
foreach (var selectedhouse in availableHouses)
{
...
}
However, I think this approach is wrong and my queries are wrong here. How can I resolve this?
Can you not add a property to your House object such as :
public House()
{
...
public bool HasBeenAssigned
{
get;
set;
}
}
Then use LINQ in order to select only those House objects that have not been assigned yet
public List<House> AvailableHouses
{
return ListOFHouses.Where(house => !house.HasBeenAssigned).Select(item => item).toList();
}
In regards to which method to adopt I would suggest - as per its use in my answer LINQ.
There is nothing wrong with the foreach loop - however as you can see the LINQ statement is more readable, maintainable, elegant and its shows intend.
The use of Where clause would be more appropriate in this case - we are looking in the list of house where
the value of HasBeenAssigned is false. This will return a list on enumerable which we select and we cast as a list.
We are not interested if there are any
which implies a boolean result. In fact the Any clause will return a boolean list.