def    __lowercase     (						lowerCamelCase					:     Any  ,  lowerCamelCase					:     List[str]  ,  lowerCamelCase					:     Optional[Any]  ,  lowerCamelCase					:     str	):
 global f  # a global dp table for knapsack
 if f[i][j] < 0:
  if j < wt[i - 1]:
   UpperCamelCase_					:						int =					mf_knapsack(i - 1  ,  lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase	)
  else:
   UpperCamelCase_					:						Tuple =					max(
       mf_knapsack(i - 1  ,  lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase	)  ,  mf_knapsack(i - 1  ,  lowerCamelCase  ,  lowerCamelCase  ,  j - wt[i - 1]	) + val[i - 1]  ,  )
  UpperCamelCase_					:						str =					val
 return f[i][j]





def    __lowercase     (						lowerCamelCase					:     List[Any]  ,  lowerCamelCase					:     Dict  ,  lowerCamelCase					:     List[str]  ,  lowerCamelCase					:     str	):
 UpperCamelCase_					:						Union[str, Any] =					[[0] * (w + 1) for _ in range(n + 1	)]

 for i in range(1  ,  n + 1	):
  for w_ in range(1  ,  w + 1	):
   if wt[i - 1] <= w_:
    UpperCamelCase_					:						str =					max(val[i - 1] + dp[i - 1][w_ - wt[i - 1]]  ,  dp[i - 1][w_]	)
   else:
    UpperCamelCase_					:						Tuple =					dp[i - 1][w_]

 return dp[n][w_], dp





def    __lowercase     (						lowerCamelCase					:     int  ,  lowerCamelCase					:     list  ,  lowerCamelCase					:     list	):
 if not (isinstance(lowerCamelCase  ,  (list, tuple)	) and isinstance(lowerCamelCase  ,  (list, tuple)	)):
  raise ValueError(
      'Both the weights and values vectors must be either lists or tuples'	)

 UpperCamelCase_					:						Any =					len(lowerCamelCase	)
 if num_items != len(lowerCamelCase	):
  UpperCamelCase_					:						Tuple =					(
      'The number of weights must be the same as the number of values.\n'
      F"But got {num_items} weights and {len(lowerCamelCase	)} values"
  )
  raise ValueError(lowerCamelCase	)
 for i in range(lowerCamelCase	):
  if not isinstance(wt[i]  ,  lowerCamelCase	):
   UpperCamelCase_					:						int =					(
       'All weights must be integers but got weight of '
       F"type {type(wt[i]	)} at index {i}"
   )
   raise TypeError(lowerCamelCase	)

 UpperCamelCase_, UpperCamelCase_					:						Optional[int] =					knapsack(lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase	)
 UpperCamelCase_					:						set =					set()
 _construct_solution(lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase  ,  lowerCamelCase	)

 return optimal_val, example_optional_set





def    __lowercase     (						lowerCamelCase					:     list  ,  lowerCamelCase					:     list  ,  lowerCamelCase					:     int  ,  lowerCamelCase					:     int  ,  lowerCamelCase					:     set	):
 # for the current item i at a maximum weight j to be part of an optimal subset,
 # the optimal value at (i, j) must be greater than the optimal value at (i-1, j).
 # where i - 1 means considering only the previous items at the given maximum weight
 if i > 0 and j > 0:
  if dp[i - 1][j] == dp[i][j]:
   _construct_solution(lowerCamelCase  ,  lowerCamelCase  ,  i - 1  ,  lowerCamelCase  ,  lowerCamelCase	)
  else:
   optimal_set.add(lowerCamelCase	)
   _construct_solution(lowerCamelCase  ,  lowerCamelCase  ,  i - 1  ,  j - wt[i - 1]  ,  lowerCamelCase	)


if __name__ == "__main__":
   a_    					=       [3, 2, 4, 4]
   a_    					=       [4, 3, 2, 3]
   a_    					=       4
   a_    					=       6
   a_    					=       [[0] * (w + 1)] + [[0] + [-1] * (w + 1) for _ in range(n + 1)]
   a_					, a_    					=       knapsack(w, wt, val, n)
   print(optimal_solution)
   print(mf_knapsack(n, wt, val, w))  # switched the n and w

   # testing the dynamic programming problem with example
   # the optimal subset for the above example are items 3 and 4
   a_					, a_    					=       knapsack_with_example_solution(w, wt, val)
   assert optimal_solution == 8
   assert optimal_subset == {3, 4}
   print('optimal_value = ', optimal_solution)
   print('An optimal subset corresponding to the optimal value', optimal_subset)




from maths.prime_check import is_prime





def    __lowercase     (						lowerCamelCase					:     int	):
 if not isinstance(lowerCamelCase  ,  lowerCamelCase	):
  UpperCamelCase_					:						List[str] =					F"Input value of [number={number}] must be an integer"
  raise TypeError(lowerCamelCase	)
 if is_prime(lowerCamelCase	) and is_prime(number + 2	):
  return number + 2
 else:
  return -1


if __name__ == "__main__":
   import doctest

   doctest.testmod()



