"""simple docstring"""



def  _A(		lowerCAmelCase							):
							if not head:
														return True
							# split the list to two parts
							A__				,							A__       :     Tuple								=			head.next, head
							while fast and fast.next:
														A__       :     Union[str, Any]								=			fast.next.next
														A__       :     Optional[Any]								=			slow.next
							A__       :     Optional[Any]								=			slow.next
							A__       :     str								=			None  # Don't forget here! But forget still works!
							# reverse the second part
							A__       :     List[str]								=			None
							while second:
														A__       :     Dict								=			second.next
														A__       :     Dict								=			node
														A__       :     Optional[Any]								=			second
														A__       :     Any								=			nxt
							# compare two parts
							# second part has the same or one less node
							while node:
														if node.val != head.val:
																					return False
														A__       :     str								=			node.next
														A__       :     Optional[int]								=			head.next
							return True

def  _A(		lowerCAmelCase							):
							if not head or not head.next:
														return True

							# 1. Get the midpoint (slow)
							A__       :     Any								=			head
							while fast and fast.next:
														A__				,							A__       :     Optional[int]								=			fast.next.next, slow.next

							# 2. Push the second half into the stack
							A__       :     Dict								=			[slow.val]
							while slow.next:
														A__       :     List[Any]								=			slow.next
														stack.append(slow.val							)

							# 3. Comparison
							while stack:
														if stack.pop() != cur.val:
																					return False
														A__       :     int								=			cur.next

							return True



def  _A(		lowerCAmelCase							):
							if not head or not head.next:
														return True
							A__       :     Optional[Any]								=			{}
							A__       :     Union[str, Any]								=			0
							while head:
														if head.val in d:
																					d[head.val].append(lowerCAmelCase							)
														else:
																					A__       :     Optional[Any]								=			[pos]
														A__       :     List[Any]								=			head.next
														pos += 1
							A__       :     Dict								=			pos - 1
							A__       :     Any								=			0
							for v in d.values():
														if len(lowerCAmelCase							) % 2 != 0:
																					middle += 1
														else:
																					A__       :     Optional[Any]								=			0
																					for i in range(0			,  len(lowerCAmelCase							)							):
																												if v[i] + v[len(lowerCAmelCase							) - 1 - step] != checksum:
																																			return False
																												step += 1
														if middle > 1:
																					return False
							return True






"""simple docstring"""



from collections import defaultdict
class 						__UpperCAmelCase    :







			'''simple docstring'''





			def __init__(			self   ,      snake_case_   ,      snake_case_							):







										'''simple docstring'''


										A__       :     Tuple								=			total  # total no of tasks (N)

										# DP table will have a dimension of (2^M)*N
										# initially all values are set to -1
										A__       :     Optional[int]								=			[
										    [-1 for i in range(total + 1							)] for j in range(2 ** len(snake_case_							)							)
										]

										A__       :     Optional[int]								=			defaultdict(snake_case_							)  # stores the list of persons for each task

										# final_mask is used to check if all persons are included by setting all bits
										# to 1
										A__       :     Optional[int]								=			(1 << len(snake_case_							)) - 1





			def 		lowerCamelCase					(			self   ,      snake_case_   ,      snake_case_							):







										'''simple docstring'''


										if mask == self.final_mask:
																	return 1

										# if not everyone gets the task and no more tasks are available, return 0
										if task_no > self.total_tasks:
																	return 0

										# if case already considered
										if self.dp[mask][task_no] != -1:
																	return self.dp[mask][task_no]

										# Number of ways when we don't this task in the arrangement
										A__       :     Optional[int]								=			self.count_ways_until(snake_case_   ,      task_no + 1							)

										# now assign the tasks one by one to all possible persons and recursively
										# assign for the remaining tasks.
										if task_no in self.task:
																	for p in self.task[task_no]:
																								# if p is already given a task
																								if mask & (1 << p):
																															continue

																								# assign this task to p and change the mask value. And recursively
																								# assign tasks with the new mask value.
																								total_ways_util += self.count_ways_until(mask | (1 << p)   ,      task_no + 1							)

        # save the value.
										A__       :     List[str]								=			total_ways_util

										return self.dp[mask][task_no]





			def 		lowerCamelCase					(			self   ,      snake_case_							):







										'''simple docstring'''


										for i in range(len(snake_case_							)							):
																	for j in task_performed[i]:
																								self.task[j].append(snake_case_							)

        # call the function to fill the DP table, final answer is stored in dp[0][1]
										return self.count_ways_until(0   ,      1							)


if __name__ == "__main__":
				_UpperCamelCase								=		5  # total no of tasks (the value of N)

				# the list of tasks that can be done by M persons.
				_UpperCamelCase								=		[[1, 3, 4], [1, 2, 5], [3, 4]]
				print(
				    AssignmentUsingBitmask(task_performed, total_tasks).count_no_of_ways(
				        task_performed
				    )
				)





