Skip to content

CadetCareerProblem – Value Parameter Specifications Methods

set_value_parameters(vp_name=None)

Set the Active Value Parameters for the Current Problem Instance.

This method assigns the current working set of value parameters (self.value_parameters) based on a given name from the value parameter dictionary (self.vp_dict). These value parameters determine cadet-level utilities, preferences, or constraints and are essential inputs to various components of the AFCCP model (e.g., CAVE, ALERT, MARKET).

If no vp_name is specified, the method defaults to the first entry in the dictionary.

Parameters:
  • vp_name (str, optional): Name of the value parameter set to activate. If None, defaults to the first available set.
Returns:

None: Updates self.vp_name and self.value_parameters in-place.

Examples:
instance.set_value_parameters()  # Automatically select the first available VP set
Source code in afccp/main.py
1789
1790
1791
1792
1793
1794
1795
1796
1797
1798
1799
1800
1801
1802
1803
1804
1805
1806
1807
1808
1809
1810
1811
1812
1813
1814
1815
1816
1817
1818
1819
1820
1821
1822
1823
1824
1825
1826
1827
1828
1829
1830
def set_value_parameters(self, vp_name=None):
    """
    Set the Active Value Parameters for the Current Problem Instance.

    This method assigns the current working set of value parameters (`self.value_parameters`) based on
    a given name from the value parameter dictionary (`self.vp_dict`). These value parameters determine
    cadet-level utilities, preferences, or constraints and are essential inputs to various components
    of the AFCCP model (e.g., CAVE, ALERT, MARKET).

    If no `vp_name` is specified, the method defaults to the first entry in the dictionary.

    Parameters:
    --------
    - vp_name (str, optional): Name of the value parameter set to activate. If None, defaults to the first available set.

    Returns:
    --------
    None: Updates `self.vp_name` and `self.value_parameters` in-place.

    Examples:
    --------
    ```python
    instance.set_value_parameters()  # Automatically select the first available VP set
    ```
    """
    if self.vp_dict is None:
        raise ValueError("Error. No sets of value parameters (vp_dict) detected. You need to import the "
                         "defaults first by using 'instance.import_default_value_parameters()'.")
    else:
        if vp_name is None:  # Name not specified
            self.vp_name = list(self.vp_dict.keys())[0]  # Take the first set in the dictionary
            self.value_parameters = copy.deepcopy(self.vp_dict[self.vp_name])
        else:  # Name specified
            if vp_name not in self.vp_dict:
                raise ValueError(vp_name + ' set not in value parameter dictionary. Available sets are:',
                                 self.vp_dict.keys())
            else:
                self.value_parameters = copy.deepcopy(self.vp_dict[vp_name])
                self.vp_name = vp_name

        if self.solution is not None:
            self.measure_solution()

update_value_parameters(num_breakpoints=24)

Simple method to take the current set of value parameters and update their sets and subsets and all that. This method also updates the set of value parameters in the dictionary

Parameters:

Name Type Description Default
num_breakpoints

Number of breakpoints to use when building the value functions

24
Source code in afccp/main.py
1832
1833
1834
1835
1836
1837
1838
1839
1840
1841
1842
1843
1844
1845
1846
1847
1848
1849
1850
def update_value_parameters(self, num_breakpoints=24):
    """
    Simple method to take the current set of value parameters and update their sets and subsets and all that.
    This method also updates the set of value parameters in the dictionary
    :param num_breakpoints: Number of breakpoints to use when building the value functions
    """

    # Update the value functions and cadet/AFSC weights
    self.value_parameters = afccp.data.values.update_value_and_weight_functions(self, num_breakpoints)

    # "Condense" the value functions by removing unnecessary zeros in the breakpoints
    self.value_parameters = afccp.data.values.condense_value_functions(self.parameters, self.value_parameters)

    # Add indexed sets and subsets of AFSCs and AFSC objectives
    self.value_parameters = afccp.data.values.value_parameters_sets_additions(
        self.parameters, self.value_parameters)

    # Update the set of value parameters in the dictionary (vp_dict attribute)
    self._update_value_parameters_in_dict()

calculate_afocd_value_parameters()

This method calculates the AFOCD value parameters using my own methodology on determining the weights and uses the AFSCs.csv dataset for the targets and constraints.

Source code in afccp/main.py
1852
1853
1854
1855
1856
1857
1858
1859
1860
1861
1862
1863
def calculate_afocd_value_parameters(self):
    """
    This method calculates the AFOCD value parameters using my own methodology on determining the
    weights and uses the AFSCs.csv dataset for the targets and constraints.
    """

    # Determine the AFOCD value parameters
    self.value_parameters = afccp.data.values.generate_afocd_value_parameters(
        self.parameters, self.value_parameters)

    # Update the value parameters
    self.update_value_parameters()

export_value_parameters_as_defaults(filename=None, printing=None)

This method exports the current set of instance value parameters to a new excel file in the "default" value parameter format

Source code in afccp/main.py
1865
1866
1867
1868
1869
1870
1871
1872
1873
1874
1875
1876
1877
1878
1879
1880
def export_value_parameters_as_defaults(self, filename=None, printing=None):
    """
    This method exports the current set of instance value parameters to a new excel file in the "default"
    value parameter format
    """
    if printing is None:
        printing = self.printing

    if self.value_parameters is None:
        raise ValueError('No instance value parameters detected.')

    # Export value parameters
    if filename is None:  # I add the "_New" just so we make sure we don't accidentally overwrite the old one
        filename = "Value_Parameters_Defaults_" + self.data_name + "_New.xlsx"
    filepath = afccp.globals.paths["support"] + "value parameters defaults/" + filename
    afccp.data.values.model_value_parameters_to_defaults(self, filepath=filepath, printing=printing)

change_weight_function(cadets=True, function=None)

Changes the weight function on either cadets or AFSCs

Parameters:

Name Type Description Default
cadets

if this is for cadets (True) or AFSCs (False)

True
function

new weight function to use

None
Source code in afccp/main.py
1882
1883
1884
1885
1886
1887
1888
1889
1890
1891
1892
1893
1894
1895
1896
1897
1898
1899
1900
1901
1902
1903
1904
1905
1906
1907
1908
1909
1910
1911
1912
1913
1914
1915
1916
1917
1918
1919
def change_weight_function(self, cadets=True, function=None):
    """
    Changes the weight function on either cadets or AFSCs
    :param cadets: if this is for cadets (True) or AFSCs (False)
    :param function: new weight function to use
    """

    if cadets:
        if function is None:
            function = 'Linear'

        if "merit_all" in self.parameters:  # The cadets' real order of merit
            merit = self.parameters["merit_all"]
        else:  # The cadets' scaled order of merit (based solely on Non-Rated cadets)
            merit = self.parameters["merit"]

        # Update weight function
        self.value_parameters['cadet_weight_function'] = function

        # Update weights
        self.value_parameters["cadet_weight"] = \
            afccp.data.values.cadet_weight_function(merit, function)

    else:
        if function is None:
            function = "Curve_2"

        if "pgl" in self.parameters:  # The actual PGL target
            quota = self.parameters["pgl"]
        else:  # The "Real" Target based on surplus and such
            quota = self.parameters["quota"]

        # Update weight function
        self.value_parameters['afsc_weight_function'] = function

        # Update weights
        self.value_parameters["afsc_weight"] = \
            afccp.data.values.afsc_weight_function(quota, function)

vft_to_gp_parameters(p_dict={}, printing=None)

Translate VFT Model Parameters to former Lt Rebecca Reynold's Goal Programming Model Parameters.

This method is responsible for translating various parameters and settings used in the Value Focussed Thinking (VFT) model into parameters suitable for the Goal Programming (GP) model. It facilitates the conversion between different modeling frameworks.

Args: p_dict (dict, optional): A dictionary of additional parameters that can be provided to fine-tune the translation process. These parameters may include specific weights or settings required for the GP model. Defaults to an empty dictionary.

printing (bool, optional): A flag to control whether to print progress information during the translation process.
    If True, it will print status updates; if False, it will run silently. Defaults to None.

Returns: None

The method updates the internal representation of parameters and settings in the instance to match the requirements of the Goal Programming (GP) model. It translates preference scores, rewards, and penalties according to the GP model's specifications, making the instance ready for goal-based optimization.

Note: - The method may apply normalization to ensure that rewards and penalties are consistent with the GP model's expectations. - If the 'get_new_rewards_penalties' flag is set to True in the model parameters, the method may compute new rewards and penalties based on the instance data and preferences, creating a fresh set of values for optimization.

Source code in afccp/main.py
1921
1922
1923
1924
1925
1926
1927
1928
1929
1930
1931
1932
1933
1934
1935
1936
1937
1938
1939
1940
1941
1942
1943
1944
1945
1946
1947
1948
1949
1950
1951
1952
1953
1954
1955
1956
1957
1958
1959
1960
1961
1962
1963
1964
1965
1966
1967
1968
1969
1970
1971
1972
1973
1974
1975
1976
1977
1978
1979
1980
1981
1982
1983
1984
1985
1986
1987
1988
1989
1990
1991
def vft_to_gp_parameters(self, p_dict={}, printing=None):
    """
    Translate VFT Model Parameters to *former* Lt Rebecca Reynold's Goal Programming Model Parameters.

    This method is responsible for translating various parameters and settings used in the Value Focussed Thinking (VFT) model
    into parameters suitable for the Goal Programming (GP) model. It facilitates the conversion between different modeling
    frameworks.

    Args:
        p_dict (dict, optional): A dictionary of additional parameters that can be provided to fine-tune the translation process.
            These parameters may include specific weights or settings required for the GP model. Defaults to an empty dictionary.

        printing (bool, optional): A flag to control whether to print progress information during the translation process.
            If True, it will print status updates; if False, it will run silently. Defaults to None.

    Returns:
        None

    The method updates the internal representation of parameters and settings in the instance to match the requirements
    of the Goal Programming (GP) model. It translates preference scores, rewards, and penalties according to the GP model's
    specifications, making the instance ready for goal-based optimization.

    Note:
    - The method may apply normalization to ensure that rewards and penalties are consistent with the GP model's expectations.
    - If the 'get_new_rewards_penalties' flag is set to True in the model parameters, the method may compute new rewards
      and penalties based on the instance data and preferences, creating a fresh set of values for optimization.

    """

    if printing is None:
        printing = self.printing

    # Print statement
    if printing:
        print('Translating VFT model parameters to Goal Programming Model parameters...')

    # Reset instance model parameters
    self._reset_functional_parameters(p_dict)

    # Get basic parameters (May or may not include penalty/reward parameters
    self.gp_parameters = afccp.data.values.translate_vft_to_gp_parameters(self)

    # Get list of constraints
    con_list = copy.deepcopy(self.gp_parameters['con'])
    con_list.append("S")
    num_constraints = len(con_list)

    # Convert gp_df to dictionary of numpy arrays ("gc" = "gp_df columns")
    gc = {col: np.array(self.gp_df[col]) for col in self.gp_df}

    # Do we want to create new rewards/penalties for this problem instance by iterating with the model?
    if self.mdl_p["get_new_rewards_penalties"]:

        gc["Raw Reward"], gc["Raw Penalty"] = afccp.solutions.optimization.calculate_rewards_penalties(
            self, printing=printing)
        min_p = min([penalty for penalty in gc["Raw Penalty"] if penalty != 0])
        min_r = min(gc["Raw Reward"])
        gc["Normalized Penalty"] = np.array([min_p / penalty if penalty != 0 else 0 for penalty in gc["Raw Penalty"]])
        gc["Normalized Reward"] = np.array([min_r / reward for reward in gc["Raw Reward"]])

    # Rewards/Penalties used in the model "run"
    gc["Run Penalty"] = np.array(
        [gc["Penalty Weight"][c] /
         gc["Normalized Penalty"][c] if gc["Normalized Penalty"][c] != 0 else 0 for c in range(num_constraints)])
    gc["Run Reward"] = np.array([gc["Reward Weight"][c] / gc["Normalized Reward"][c] for c in range(num_constraints)])

    # Convert back to pandas dataframe using numpy array dictionary
    self.gp_df = pd.DataFrame(gc)

    # Update the "mu" and "lam" parameters with our new Reward/Penalty terms
    self.gp_parameters = afccp.data.values.translate_vft_to_gp_parameters(self)