def _evaluate(self,
                  x,  #
                  out,
                  *args,
                  **kwargs):
        """
        This method iterate over an Individual, execute the refactoring operation sequentially,
        and compute quality attributes for the refactored version of the program, as objectives of the search

        params:
        x (Individual): x is an instance of Individual (i.e., a list of refactoring operations)

        """
        # Stage 0: Git restore
        logger.debug("Executing git restore.")
        git_restore(config.PROJECT_PATH)
        update_understand_database(config.UDB_PATH)
        # Stage 1: Execute all refactoring operations in the sequence x
        logger.debug(f"Reached Individual with Size {len(x[0])}")
        for refactoring_operation in x[0]:
            refactoring_operation.do_refactoring()
            # Update Understand DB
            update_understand_database(config.UDB_PATH)

        # Stage 2: Computing quality attributes
        obj = DesignQualityAttributes(udb_path=config.UDB_PATH)
        o1 = obj.average_sum
        del obj
        o2 = testability_main(config.UDB_PATH)
        o3 = modularity_main(config.UDB_PATH)
        logger.info(f"QMOOD AVG Score: {o1}")
        logger.info(f"Testability Score: {o2}")
        logger.info(f"Modularity Score: {o3}")
        # Stage 3: Marshal objectives into vector
        out["F"] = np.array([-1 * o1, -1 * o2, -1 * o3], dtype=float)
示例#2
0
    def execute_from_txt_log(self, input_file_path):
        """
        input_file_path: The path of input data from log.

        Example: Take a look at ./input.txt
        """

        with open(input_file_path, 'r') as f:
            data = f.read().split('\n')

        for row in data:
            refactoring_name = re.search(', (.+?)(\w+)*\(',
                                         row).group()[1:-1].strip()
            params = re.search('{(.+?)}', row).group().strip()
            params = params.replace("'", '"')
            params = params.replace("False", "false")
            params = params.replace("True", "true")
            params = json.loads(params)

            if params.get('udb_path'):
                params['udb_path'] = config.UDB_PATH
            if params.get('project_dir'):
                params['project_dir'] = config.PROJECT_PATH
            if params.get('file_path'):
                params['file_path'] = params['file_path'].replace(
                    self.file_path_base_dir_old, config.PROJECT_ROOT_DIR)
            print(refactoring_name, params)

            res = REFACTORING_MAIN_MAP[refactoring_name](**params)
            print(f"Executed {refactoring_name} with status {res}")
            update_understand_database(config.UDB_PATH)
            print('-' * 100)
示例#3
0
    def _evaluate(self,
                  x,  #
                  out,
                  *args,
                  **kwargs):
        """

        This method iterate over a population, execute the refactoring operations in each individual sequentially,
        and compute quality attributes for the refactored version of the program, as objectives of the search

        Args:

            x (Population): x is a matrix where each row is an individual, and each column a variable. \
            We have one variable of type list (Individual) ==> x.shape = (len(Population), 1)


        """
        objective_values = []
        for k, individual_ in enumerate(x):
            # Stage 0: Git restore
            logger.debug("Executing git restore.")
            git_restore(config.PROJECT_PATH)
            logger.debug("Updating understand database after git restore.")
            update_understand_database(config.UDB_PATH)

            # Stage 1: Execute all refactoring operations in the sequence x
            logger.debug(f"Reached Individual with Size {len(individual_[0])}")
            for refactoring_operation in individual_[0]:
                refactoring_operation.do_refactoring()
                # Update Understand DB
                logger.debug(f"Updating understand database after {refactoring_operation.name}.")
                update_understand_database(config.UDB_PATH)

            # Stage 2:
            arr = Array('d', range(self.n_obj_virtual))
            if self.evaluate_in_parallel:
                # Stage 2 (parallel mood): Computing quality attributes
                p1 = Process(target=calc_qmood_objectives, args=(arr,))
                p2 = Process(target=calc_testability_objective, args=(config.UDB_PATH, arr,))
                p3 = Process(target=calc_modularity_objective, args=(config.UDB_PATH, arr,))
                p1.start(), p2.start(), p3.start()
                p1.join(), p2.join(), p3.join()
                o1 = sum([i for i in arr[:6]]) / 6.
                o2 = arr[6]
                o3 = arr[7]
            else:
                # Stage 2 (sequential mood): Computing quality attributes
                qmood_quality_attributes = DesignQualityAttributes(udb_path=config.UDB_PATH)
                o1 = qmood_quality_attributes.average_sum
                o2 = testability_main(config.UDB_PATH, initial_value=config.CURRENT_METRICS.get("TEST", 1.0))
                o3 = modularity_main(config.UDB_PATH, initial_value=config.CURRENT_METRICS.get("MODULE", 1.0))
                del qmood_quality_attributes

            # Stage 3: Marshal objectives into vector
            objective_values.append([-1 * o1, -1 * o2, -1 * o3])
            logger.info(f"Objective values for individual {k}: {[-1 * o1, -1 * o2, -1 * o3]}")

        # Stage 4: Marshal all objectives into out dictionary
        out['F'] = np.array(objective_values, dtype=float)
    def _evaluate(
            self,
            x,  #
            out,
            *args,
            **kwargs):
        """
        This method iterate over an Individual, execute the refactoring operation sequentially,
        and compute quality attributes for the refactored version of the program, as objectives of the search

        params:
        x (Individual): x is an instance of Individual (i.e., a list of refactoring operations)

        """
        # Git restore`
        logger.debug("Executing git restore.")
        git_restore(config.PROJECT_PATH)
        update_understand_database(config.UDB_PATH)
        # Stage 1: Execute all refactoring operations in the sequence x
        logger.debug(f"Reached Individual with Size {len(x[0])}")
        for refactoring_operation in x[0]:
            refactoring_operation.do_refactoring()
            # Update Understand DB
            update_understand_database(config.UDB_PATH)

        # Stage 2: Computing quality attributes
        qmood = DesignQualityAttributes(udb_path=config.UDB_PATH)
        o1 = qmood.reusability
        o2 = qmood.understandability
        o3 = qmood.flexibility
        o4 = qmood.functionality
        o5 = qmood.effectiveness
        o6 = qmood.extendability
        del qmood
        o7 = testability_main(config.UDB_PATH)
        o8 = modularity_main(config.UDB_PATH)

        logger.info(f"Reusability Score: {o1}")
        logger.info(f"Understandability Score: {o2}")
        logger.info(f"Flexibility Score: {o3}")
        logger.info(f"Functionality Score: {o4}")
        logger.info(f"Effectiveness Score: {o5}")
        logger.info(f"Extendability Score: {o6}")
        logger.info(f"Testability Score: {o7}")
        logger.info(f"Modularity Score: {o8}")

        # Stage 3: Marshal objectives into vector
        out["F"] = np.array([
            -1 * o1,
            -1 * o2,
            -1 * o3,
            -1 * o4,
            -1 * o5,
            -1 * o6,
            -1 * o7,
            -1 * o8,
        ],
                            dtype=float)
示例#5
0
    )

    # Post-Paste: Reference Injection
    parse_and_walk(
        file_path=target_class_file,
        listener_class=ReferenceInjectorAndConstructorListener,
        has_write=True,
        method_text=method_text,
        source_class=source_class,
        method_map=method_map,
        imports=None,
        has_empty_cons=listener.has_empty_cons,
    )
    # db.close()
    return True


# Tests
if __name__ == '__main__':
    from codart.utility.directory_utils import update_understand_database

    update_understand_database("C:/Users/Administrator/Downloads/udbs/jvlt-1.3.2.udb")
    main(
        source_class="XMLFormatter",
        source_package="net.sourceforge.jvlt.io",
        target_class="Entry",
        target_package="net.sourceforge.jvlt.core",
        method_name="getXMLForEntryInfo",
        udb_path="C:/Users/Administrator/Downloads/udbs/jvlt-1.3.2.udb"
    )
示例#6
0
    def execute_from_json_log(self, input_file_path=None, reset=True):
        if input_file_path is None:
            input_file_path = glob.glob(
                os.path.join(self.log_directory,
                             'best_refactoring_sequences*.json'))[0]

        # log_project_info(reset_=True, )

        population = []
        with open(input_file_path, 'r', encoding='utf-8') as fp:
            population_trimmed = json.load(fp)

        for chromosome in population_trimmed:
            chromosome_new = []
            for gene_ in chromosome:
                refactoring_params = gene_[1]
                if refactoring_params.get('udb_path'):
                    refactoring_params['udb_path'] = config.UDB_PATH
                if refactoring_params.get('project_dir'):
                    refactoring_params['project_dir'] = config.PROJECT_PATH
                if refactoring_params.get('file_path'):
                    refactoring_params['file_path'] = refactoring_params[
                        'file_path'].replace(self.file_path_base_dir_old,
                                             config.PROJECT_ROOT_DIR)
                if refactoring_params.get('class_path'):
                    refactoring_params['class_path'] = refactoring_params[
                        'class_path'].replace(self.file_path_base_dir_old,
                                              config.PROJECT_ROOT_DIR)
                chromosome_new.append((REFACTORING_MAIN_MAP[gene_[0]],
                                       refactoring_params, gene_[0]))
            population.append(chromosome_new)

        # print(population)
        # quit()
        applicability_map = {
            'Project': [],
            'Sequence': [],
            'Applied refactorings': [],
            'Rejected refactorings': []
        }
        for k, refactoring_sequence in enumerate(population):
            true_refactorings_count = 0
            false_refactorings_count = 0
            reset_project()

            # Apply sequence X to system S
            for refactoring_operation in refactoring_sequence:
                res = refactoring_operation[0](**refactoring_operation[1])
                update_understand_database(config.UDB_PATH)
                if res:
                    true_refactorings_count += 1
                else:
                    false_refactorings_count += 1
                config.logger.info(
                    f"Executed {refactoring_operation[2]} with status {res}")

            applicability_map['Project'].append(config.PROJECT_NAME)
            applicability_map['Sequence'].append(k)
            applicability_map['Applied refactorings'].append(
                true_refactorings_count)
            applicability_map['Rejected refactorings'].append(
                false_refactorings_count)

            continue

            # Dump refactored project
            dump_path = os.path.join(
                config.PROJECT_ROOT_DIR,
                f'{config.PROJECT_NAME}_refactored_with_algorithm{config.PROBLEM}_rand',
                f'dump{k}')

            if not os.path.exists(config.PROJECT_ROOT_DIR):
                os.mkdir(dump_path)

            shutil.copytree(config.PROJECT_PATH, dump_path)

            # Compute quality metrics
            log_project_info(
                reset_=False,
                quality_attributes_path=os.path.join(
                    config.PROJECT_LOG_DIR,
                    'best_refactoring_sequences_objectives_extended.csv'),
                generation='-1',  # config.MAX_ITERATIONS,
                testability_verbose=True,
                testability_log_path=os.path.join(
                    config.PROJECT_LOG_DIR,
                    f'classes_testability2_for_problem_{config.PROBLEM}_best_sequence_{k}.csv'
                ))

        # Log applied and rejected refactorings
        df = pd.DataFrame(data=applicability_map)
        df.to_csv(os.path.join(config.PROJECT_LOG_DIR,
                               'applicability_map.csv'),
                  index=False)

        if reset:
            reset_project()
示例#7
0
        ]
        all_metrics = []
        for metric in attrs:
            cache = getattr(self, f'_{metric}')
            if cache is None:
                all_metrics.append(getattr(self, metric))
            else:
                all_metrics.append(cache)
        return round(sum(all_metrics) / len(all_metrics),
                     5), round(sum(all_metrics), 5)


if __name__ == '__main__':
    from codart.utility.directory_utils import update_understand_database

    update_understand_database(config.UDB_PATH)
    print(f"UDB path: {config.UDB_PATH}")

    design_quality_attribute = DesignQualityAttributes(config.UDB_PATH)
    metrics_dict = {
        "DSC": design_quality_attribute.DSC,
        "NOH": design_quality_attribute.NOH,
        "ANA": design_quality_attribute.ANA,
        "MOA": design_quality_attribute.MOA,
        "DAM": design_quality_attribute.DAM,
        "CAMC": design_quality_attribute.CAMC,
        "CIS": design_quality_attribute.CIS,
        "NOM": design_quality_attribute.NOM,
        "DCC": design_quality_attribute.DCC,
        "MFA": design_quality_attribute.MFA,
        "NOP": design_quality_attribute.NOP
示例#8
0
# Random search for improving reusability
while k < MAX_ITERATIONS and limit > 0:
    print("Iteration No.", k)
    index = random.randint(0, limit - 1)
    limit -= 1
    print(f"index is {index}")
    individual = rand_pop.pop(index)
    print(f"len(individual) is {len(individual)}")
    # git restore prev changes
    git_restore(project_dir)
    # execute individual
    for refactoring, params in individual:
        print(params)
        try:
            refactoring(**params)
        except Exception as e:
            print(e)
        # update understand database
        update_understand_database(udb_path)
    # calculate objective
    obj_score = DesignQualityAttributes(udb_path=udb_path).reusability
    print("Objective Score", obj_score)
    if obj_score < score:
        score = obj_score
        best_answer = individual
    k += 1

print("=" * 75)
print("Best Score", score)
print("Best Answer", best_answer)
示例#9
0
    def _evaluate(self, x, out, *args, **kwargs):
        """

        This method iterate over a population, execute the refactoring operations in each individual sequentially,
        and compute quality attributes for the refactored version of the program, as objectives of the search.
        By default, elementwise_evaluation is set to False, which implies the _evaluate retrieves a set of solutions.

        Args:

            x (Population): x is a matrix where each row is an individual, and each column a variable.\
            We have one variable of type list (Individual) ==> x.shape = (len(Population), 1)


        """

        objective_values = []
        for k, individual_ in enumerate(x):
            # Stage 0: Git restore
            logger.debug("Executing git restore.")
            git_restore(config.PROJECT_PATH)
            logger.debug("Updating understand database after git restore.")
            update_understand_database(config.UDB_PATH)

            # Stage 1: Execute all refactoring operations in the sequence x
            logger.debug(f"Reached an Individual with size {len(individual_[0])}")
            for refactoring_operation in individual_[0]:
                res = refactoring_operation.do_refactoring()
                # Update Understand DB
                logger.debug(f"Updating understand database after {refactoring_operation.name}.")
                update_understand_database(config.UDB_PATH)

            # Stage 2:
            arr = Array('d', range(self.n_obj))
            if self.evaluate_in_parallel:
                # Stage 2 (parallel mood): Computing quality attributes
                p1 = Process(target=calc_qmood_objectives, args=(arr,))
                if self.n_obj == 8:
                    p2 = Process(target=calc_testability_objective, args=(config.UDB_PATH, arr,))
                    p3 = Process(target=calc_modularity_objective, args=(config.UDB_PATH, arr,))
                    p1.start(), p2.start(), p3.start()
                    p1.join(), p2.join(), p3.join()
                else:
                    p1.start()
                    p1.join()
            else:
                # Stage 2 (sequential mood): Computing quality attributes
                qmood_quality_attributes = DesignQualityAttributes(udb_path=config.UDB_PATH)
                arr[0] = qmood_quality_attributes.reusability
                arr[1] = qmood_quality_attributes.understandability
                arr[2] = qmood_quality_attributes.flexibility
                arr[3] = qmood_quality_attributes.functionality
                arr[4] = qmood_quality_attributes.effectiveness
                arr[5] = qmood_quality_attributes.extendability
                if self.n_obj == 8:
                    arr[6] = testability_main(config.UDB_PATH, initial_value=config.CURRENT_METRICS.get("TEST", 1.0))
                    arr[7] = modularity_main(config.UDB_PATH, initial_value=config.CURRENT_METRICS.get("MODULE", 1.0))

                if self.verbose_design_metrics:
                    design_metrics = {
                        "DSC": [qmood_quality_attributes.DSC],
                        "NOH": [qmood_quality_attributes.NOH],
                        "ANA": [qmood_quality_attributes.ANA],
                        "MOA": [qmood_quality_attributes.MOA],
                        "DAM": [qmood_quality_attributes.DAM],
                        "CAMC": [qmood_quality_attributes.CAMC],
                        "CIS": [qmood_quality_attributes.CIS],
                        "NOM": [qmood_quality_attributes.NOM],
                        "DCC": [qmood_quality_attributes.DCC],
                        "MFA": [qmood_quality_attributes.MFA],
                        "NOP": [qmood_quality_attributes.NOP]
                    }
                    self.log_design_metrics(design_metrics)

                del qmood_quality_attributes

            # Stage 3: Marshal objectives into vector
            objective_values.append([-1 * i for i in arr])
            logger.info(f"Objective values for individual {k}: {[i for i in arr]}")

        # Stage 4: Marshal all objectives into out dictionary
        out['F'] = np.array(objective_values, dtype=float)