⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 art_int.c

📁 自适应共振神经网络可以实现自动学习与分类具有自适应的功能
💻 C
📖 第 1 页 / 共 4 页
字号:
                return 1;
            }
        }

        *(art->commit + art->nodes_used) = TRUE; /* Note it as now used          */

        /**< Set winner-take-all category activations                            */
        for (i = 0; i < art->nodes_used; i++) 
        {
            if (i == art->win_cat)
            {
                *(art->cat + i) = 1;
            }
            else
            {
                *(art->cat + i) = 0;
            }
        }

        /**< Fast learning for uncommited node.                       (beta = 1) */
        for (i = 0; i < art->num_inputs; i++)
        {
            *(*(art->weight + art->win_cat) + i) = Intersect((*(input + i)), (*(*(art->weight + art->win_cat) + i)), art->type);                     
        }
    }
    else 
    {
        /**< Slow Recoding for commited node.                         (beta < 1) */
        for (i = 0; i < art->num_inputs; i++)
        {
            *(*(art->weight + art->win_cat) + i) = ((art->beta) * Intersect((*(input + i)), (*(*(art->weight+art->win_cat) + i)), art->type)) + ((1 - (art->beta)) * (*(*(art->weight + art->win_cat) + i)));
        }
    }

    /**< Calculate Art weight sum for speeding up later calculations           */
    *(art->sum_weights + art->win_cat) = 0;
    for (i = 0; i < art->num_inputs; i++)
    {
        *(art->sum_weights + art->win_cat) += (*(*(art->weight + art->win_cat)+i));
    }

    return 0;
}

/**
 * \fn int AddMaps(mapPTR map)
 * \brief Add map to ARTMAP network
 * When using ARTMAP, this procedure needs to be called everytime
 * either the Art-A or Art-B networks change size (see AddCats).
 * Allocates space for more mapfield nodes based on the new sizes
 * of the Art-A and Art-B networks and sets initial values for
 * the newly allocated nodes and weights.
 * \param map the map to be added
 * \retval 0 Successful
 * \retval 1 Out of memory
 */
int AddMaps(mapPTR map)
{
    float *tempfltv;  /**< Temporary pointer for copying */
    float **tempflt;  /**< Temporary pointer for copying */
    int i,j;          /**< Counters */

    tempflt=(float **)malloc((size_t)((map->artA.max_nodes) * sizeof(float *)));
    if (tempflt == NULL)
    {
        return 1;
    }
    tempflt[0] = (float *)malloc((size_t)((map->artA.max_nodes * map->artB.max_nodes) * sizeof(float)));
    if (tempflt[0] == NULL)
    {
        free(tempflt);
        return 1;
    }
    for(i = 1; i < map->artA.max_nodes; i++)
    {
        tempflt[i] = tempflt[i-1] + map->artB.max_nodes;
    }
    for (i = 0; i < map->maxA_nodes; i++)
    {
        for (j = 0; j < map->maxB_nodes; j++)
        {
            *(*(tempflt + i) + j) = *(*(map->map_weight + i) + j);
        }
    }
    free(map->map_weight[0]);
    free(map->map_weight);
    map->map_weight = tempflt;

    tempfltv = (float *)malloc((size_t)(map->artB.max_nodes * sizeof(float)));
    if (tempfltv == NULL)
    {
        return 1;
    }
    for (i = 0; i < map->maxB_nodes; i++)
    {
        *(tempfltv + i) = *(map->map + i);
    }
    free(map->map);
    map->map = tempfltv;

    /**< Set initial weights of all new mapfield nodes */
    for (i = map->maxA_nodes; i < (map->artA.max_nodes); i++)
    {
        for (j = 0; j < map->artB.max_nodes; j++)
        {
            *(*(map->map_weight + i) + j) = 1;
        }
    }
    for (i = 0; i < map->artA.max_nodes; i++)
    {
        for (j = map->maxB_nodes; j < (map->artB.max_nodes); j++)
        {
            *(*(map->map_weight + i) + j) = 1;
        }
    }

    /**< Update mapfield values */
    map->maxA_nodes = map->artA.max_nodes;
    map->maxB_nodes = map->artB.max_nodes;

    return 0;
}

/**
 * \fn int TrainMapPat(mapPTR map, patPTR pat)
 * \brief Train the mapfield network
 *           Given a pointer to a mapfield, and a pointer to a single
 *           pattern trains the mapfield network on the pattern.
 * \param map the mapfield pointer
 * \param pat the pattern pointer
 * \retval 0 Successful
 * \retval 1 Out of memory
 */
int TrainMapPat(mapPTR map, patPTR pat) 
{
    float sum_inputs;       /**< Sum of all the active inputs                */
    float sum_cat;          /**< Sum of all the active Art-B categories      */
    float sum_map;          /**< Sum of activations of map nodes             */
    int doneB;              /**< Boolean to signal when done with pattern    */
    int i;                  /**< Counters                                    */


    /**< -------------- First activate and train Art-B network --------------- */
    /**< Find winning Art-B category                                           */
    ActivateArt(&map->artB, pat->output);

    /**< If Art-B not of type ART_TYPE_NONE train it                                    */
    if (map->artB.type != ART_TYPE_NONE) 
    { 
        if (TrainArtPat(&map->artB, pat->output)) 
        {
            return 1;
        }

        /**< Check if TrainArtPat allocated new space for ArtB                   */
        if (map->maxB_nodes != map->artB.max_nodes)
        {
            if (AddMaps(map)) 
            {
                return 1;
            }
        }
    }

    /**< -------- Find an Art-A category that meets mapfield vigilence -------- */
    doneB           = FALSE;                 /* Haven't found one yet         */
    map->artA.vigil = map->base_vigil;       /* Reset vigilence to base level */

    while (!doneB) 
    {
        /**< Find the winning category */
        ActivateArt(&map->artA, pat->input);  

        /**< When no previously used Art-A node was able to win, a new Art-A node */
        /**< is created and trained on the mapfield                               */
        if (map->artA.win_cat == -1) 
        {
            /**< Train New Unused Node in ArtA Module                               */
            if (TrainArtPat(&map->artA, pat->input)) 
            {
                return 1;
            }
            /**< Train mapfield weights for new node                                */
            for (i = 0; i < map->artB.nodes_used; i++) 
            {
                *(*(map->map_weight + map->artA.win_cat) + i) = (*(map->artB.cat + i));
            }
            /**< Check if TrainArtPat allocated new space for ArtA                  */
            if (map->maxA_nodes != map->artA.max_nodes)
            {
                if (AddMaps(map))
                {
                    return 1;
                }
            }

            doneB = TRUE;
        }

        /**< Otherwise check map vigilence for the used node                       */
        else 
        { 
            /**< Calculate Mapfield Activations */
            for (i = 0; i < map->artB.nodes_used; i++) 
            {
                /**< For each mapfield node */ 
                *(map->map + i) = (*(*(map->map_weight + map->artA.win_cat) + i)); 
            }

            sum_map = 0;
            sum_cat = 0;
            for (i = 0; i < map->artB.nodes_used; i++) 
            {
                sum_map += FuzzInt((*(map->map + i)), (*(map->artB.cat + i)));
                sum_cat += FuzzUni((*(map->map + i)), (*(map->artB.cat + i)));
            }
            if (map->artB.type != ART_TYPE_NONE)
            {
                sum_cat = 1;
            }

            /**< Calculate sum of inputs                                              */  
            sum_inputs = 0;                        /**< Note: When compliment coded,    */
            for (i = 0; i < map->artA.num_inputs; i++) /**<       sum of inputs is equal to */
            {
                sum_inputs += (*(pat->input + i));     /**<       half the network inputs.  */
            }

            /**< Check vigilence at mapfield                                           */
            if ((sum_map / sum_cat) < map->vigil) 
            {
                /**< If mapfield mismatch then ArtA isn't done                           */
                doneB = FALSE;
                /**< Error causes increase in Art-A vigilence unless doing so exceeds    */
                /**< the highest vigilence level.  If this is the case, then mismatch    */
                /**< was caused by inconsistent or noisy data so ignore and go on.       */
                map->artA.vigil = ((*(map->artA.sum_IW + map->artA.win_cat)) / sum_inputs) + 0.0001f;
                if (map->artA.vigil > 1.0) 
                {
                    doneB = TRUE;
                }
                else
                {
                    map->num_mismatch++;
                }
            }
            else 
            {      
                /**< Train mapfield weights                                              */
                for (i = 0; i < map->artB.nodes_used; i++) 
                {
                    *(*(map->map_weight + map->artA.win_cat) + i) = (*(map->artB.cat + i));
                }
                /**< Train ArtA Module                                                   */
                if (TrainArtPat(&map->artA, pat->input)) 
                {
                    return 1;
                }
                /**< Check if TrainArtPat allocated new space for ArtA                   */
                if (map->maxA_nodes != map->artA.max_nodes)
                {
                    if (AddMaps(map)) 
                    {
                        return 1;
                    }
                }
                doneB = TRUE;
            }
        }
    }
    return 0;
}

/**
 * \fn int Compliment(setTYPE *set, int input_style, int output_style)
 * \brief compilement codes members
 *     Compilement codes members of a pettern set, when specified, 
 *     allocated space for the compliment coded patterns.
 * \param set the set
 * \param input_style input style
 * \param output_style output style
 * \retval 0 Successful
 * \retval 1 out of memory
 */
int Compliment(setTYPE *set, int input_style, int output_style) 
{
    float *tempflt;
    int i,j;

    /**< If compliment coding is requested of the input patterns               */
    if (input_style == ART_STYLE_COMPLIMENT) 
    {
        /**< Allocate space for compliment coded inputs and copy old inputs      */
        for (j = 0; j < set->num_patterns; j++) 
        {
            tempflt = (float *)malloc((size_t)((2 * set->num_inputs) * sizeof(float)));
            if (tempflt == NULL) 
            {
                return 1;
            }
            for (i = 0; i < set->num_inputs; i++)
            {
                *(tempflt + i) = *(set->pattern[j].input + i);
            }
            free(set->pattern[j].input);
            set->pattern[j].input = tempflt;

            /**< Complement coding input patterns in new space                     */
            for (i = 0; i < set->num_inputs; i++)
            {
                *(set->pattern[j].input + (i + set->num_inputs)) = (1 - (*(set->pattern[j].input + i)));
            }
        }
        set->style_inputs = ART_STYLE_COMPLIMENT;
    }

    /**< If compliment coding is requested of the output patterns              */
    if (output_style == ART_STYLE_COMPLIMENT) 
    {
        /**< Allocate space for compliment coded outputs and copy old outputs    */
        for (j = 0; j < set->num_patterns; j++) 
        {
            tempflt = (float *)malloc((size_t)((2 * set->num_outputs) * sizeof(float)));
            if (tempflt == NULL) 
            {
                return 1;
            }
            for (i = 0; i < set->num_outputs; i++)
            {
                *(tempflt + i) = *(set->pattern[j].output + i);
            }
            free(set->pattern[j].output);
            set->pattern[j].output = tempflt;

            /**< Complement coding output patterns in new space                    */
            for (i = 0; i < set->num_outputs; i++) 
            {
                *(set->pattern[j].output + (i + set->num_outputs)) = (1 - (*(set->pattern[j].output + i)));
            }
        }
        set->style_outputs = ART_STYLE_COMPLIMENT;
    }
    return 0;
}

/**
 * \fn int CheckNetSet(netPTR net, setPTR set)
 * \brief Check the net compatible
 *           Given a pointer to a network and a pointer to a pattern set
 *           checks to make sure they are compatible.
 * \param net the network
 * \param set the set
 * \retval 0 No errors, they are compatible
 * \retval 3 NODE_ANALOG inputs given to NODE_BINARY network
 * \retval 4 Input Size Incompatible
 * \retval 5 Output Size Incompatible
 * \retval 6 No output patterns for ARTMAP network
 * \retval 7 Memory Allocation failure (out of memory)
 */
int CheckNetSet(netPTR net, setPTR set) 
{
    if (net->type == ART) 
    {
        /**< Check Art Component Input Type Compatibility                        */
        if ((net->art.type == ART_TYPE_ART1)&&(set->type_inputs == NODE_ANALOG))        
        {
            return 3;
        }

        if ((net->art.style == ART_STYLE_NONE)&&(net->num_inputs != set->num_inputs))                       
        {
            return 4;
        }
        if ((net->art.style == ART_STYLE_COMPLIMENT)&&(net->num_inputs != 2 * (set->num_inputs)))
        {
            return 4;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -