From 4475cfa93b7a389f51e48e2e9ac6f60cb1672c46 Mon Sep 17 00:00:00 2001 From: ppbisf2hv <1900636505@qq.com> Date: Sun, 19 Nov 2023 09:26:35 +0800 Subject: [PATCH] Update README.md --- README.md | 270 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 270 insertions(+) diff --git a/README.md b/README.md index e5f5adf..4406a77 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,272 @@ # BPnetwork +#include +#include +#include +#include +#define INNODE 2 +#define HIDENODE 12 +#define OUTNODE 1 +double StudyRate = 1.2; +double threshold = 1e-4; +int mostTimes = 1e6; +int trainSize = 0; +int testSize = 0; +typedef struct Sample{ + double out[30][OUTNODE]; + double in[30][INNODE]; +}Sample; +typedef struct Node{ + double value; + double bias; + double bias_delta; + double *weight; + double *weight_delta; +}Node; +Node inputLayer[INNODE]; +Node hideLayer[HIDENODE]; +Node outLayer[OUTNODE]; +double Max(double a, double b){ + return a > b ? a : b; +} +double sigmoid(double x){ + double y,z; + y=exp(x); + z=y/(1+y); + return z; + +} +Sample * getTrainData(const char * filename){ + Sample * result = (Sample*)malloc(sizeof (Sample)); + FILE * file = fopen(filename, "r"); + if(file != NULL){ + int count = 0; + while (fscanf(file, "%lf %lf %lf", &result->in[count][0], &result->in[count][1], &result->out[count][0]) != EOF){ + ++count; + } + trainSize = count; + printf("%s The file has been successfully read!\n", filename); + fclose(file); + return result; + } else{ + fclose(file); + printf("%s Encountered an error while opening the file!\n\a", filename); + return NULL; + } +} +Sample * getTestData(const char * filename){ + Sample * result=(Sample*)malloc(sizeof(Sample)); + FILE * file = fopen(filename, "r"); + if(file!= NULL){ + int count=0; + while (fscanf(file, "%lf %lf", &result->in[count][0], &result->in[count][1])!=EOF){ + ++count; + } + testSize=count; + printf("%s The file has been successfully read!\n", filename); + fclose(file); + return result; + }else{ + fclose(file); + printf("%s Encountered an error while opening the file!\n\a", filename); + return NULL; + } +} +void printData(Sample * data, int size){ + int i; + if(data==NULL){ + printf("Sample is empty!"); + return; + } + else{ + for(i=0;iin[i][0],data->in[i][1]); + printf("%f",data->out[i][0]); + printf("\n"); + } + } +} +void init(){ + srand(time(NULL)); + for (int i = 0; i < INNODE; ++i) { + inputLayer[i].weight = (double *)malloc(sizeof (double ) * HIDENODE); + inputLayer[i].weight_delta = (double *) malloc(sizeof (double ) * HIDENODE); + inputLayer[i].bias = 0.0; + inputLayer[i].bias_delta = 0.0; + } + for (int i = 0; i < INNODE; ++i) { + for (int j = 0; j < HIDENODE; ++j) { + inputLayer[i].weight[j] = rand() % 10000 / (double )10000 * 2 - 1.0; + inputLayer[i].weight_delta[j] = 0.0; + } + } + for (int i = 0; i < HIDENODE; ++i) { + hideLayer[i].weight = (double *)malloc(sizeof(double)*OUTNODE); + hideLayer[i].weight_delta =(double*)malloc(sizeof(double)*OUTNODE); + hideLayer[i].bias = rand() % 10000 / (double )10000 * 2 - 1.0; + hideLayer[i].bias_delta = 0.0; + } + for (int i = 0; i < HIDENODE; ++i) { + for (int j = 0; j < OUTNODE; ++j) { + hideLayer[i].weight[j] = rand() % 10000 / (double )10000 * 2 - 1.0; + hideLayer[i].weight_delta[j] = 0.0; + } + } + + for (int i = 0; i < OUTNODE; ++i) { + outLayer[i].bias = rand() % 10000 / (double )10000 * 2 - 1.0; + outLayer[i].bias_delta = 0.0; + } + +} +void resetDelta(){ + for (int i = 0; i < INNODE; ++i) { + for (int j = 0; j < HIDENODE; ++j) { + inputLayer[i].weight_delta[j] = 0.0; + } + } + + for (int i = 0; i < HIDENODE; ++i) { + hideLayer[i].bias_delta = 0.0; + for (int j = 0; j < OUTNODE; ++j) { + hideLayer[i].weight_delta[j] = 0.0; + } + } + + for (int i = 0; i < OUTNODE; ++i) { + outLayer[i].bias_delta = 0.0; + } +} +int main() { + init(); + Sample * trainSample = getTrainData("TrainData.txt"); + for (int trainTime = 0; trainTime < mostTimes; ++trainTime) { + resetDelta(); + double error_max = 0.0; + for (int currentTrainSample_Pos = 0; currentTrainSample_Pos < trainSize; ++currentTrainSample_Pos) { + for (int inputLayer_Pos = 0; inputLayer_Pos < INNODE; ++inputLayer_Pos) { + inputLayer[inputLayer_Pos].value = trainSample->in[currentTrainSample_Pos][inputLayer_Pos]; + } + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + double sum = 0.0; + for (int inputLayer_Pos = 0; inputLayer_Pos < INNODE; ++inputLayer_Pos) { + sum += inputLayer[inputLayer_Pos].value * inputLayer[inputLayer_Pos].weight[hideLayer_Pos]; + } + + sum -= hideLayer[hideLayer_Pos].bias; + hideLayer[hideLayer_Pos].value = sigmoid(sum); + } + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE ; ++outLayer_Pos) { + double sum = 0.0; + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + sum+=hideLayer[hideLayer_Pos].value * hideLayer[hideLayer_Pos].weight[outLayer_Pos]; + + } + sum-=outLayer[outLayer_Pos].bias; + outLayer[outLayer_Pos].value=sigmoid(sum); + } + double error = 0.0; + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + double temp = fabs(outLayer[outLayer_Pos].value - trainSample->out[currentTrainSample_Pos][outLayer_Pos]); + error += temp * temp / 2.0; + } + + error_max = Max(error_max, error); + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + double bias_delta = -(trainSample->out[currentTrainSample_Pos][outLayer_Pos] - outLayer[outLayer_Pos].value) + * outLayer[outLayer_Pos].value * (1.0 - outLayer[outLayer_Pos].value); + outLayer[outLayer_Pos].bias_delta += bias_delta; + } + + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + double weight_delta = (trainSample->out[currentTrainSample_Pos][outLayer_Pos] - outLayer[outLayer_Pos].value) + * outLayer[outLayer_Pos].value * (1.0 - outLayer[outLayer_Pos].value) + * hideLayer[hideLayer_Pos].value; + hideLayer[hideLayer_Pos].weight_delta[outLayer_Pos] += weight_delta; + } + } + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + double sum = 0.0; + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + sum += -(trainSample->out[currentTrainSample_Pos][outLayer_Pos] - outLayer[outLayer_Pos].value) + * outLayer[outLayer_Pos].value * (1.0 - outLayer[outLayer_Pos].value) + * hideLayer[hideLayer_Pos].weight[outLayer_Pos]; + } + hideLayer[hideLayer_Pos].bias_delta += sum * hideLayer[hideLayer_Pos].value * (1.0 - hideLayer[hideLayer_Pos].value); + } + + + for (int inputLayer_Pos = 0; inputLayer_Pos < INNODE; ++inputLayer_Pos) { + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + double sum = 0.0; + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + sum += (trainSample->out[currentTrainSample_Pos][outLayer_Pos] - outLayer[outLayer_Pos].value) + * outLayer[outLayer_Pos].value * (1.0 - outLayer[outLayer_Pos].value) + * hideLayer[hideLayer_Pos].weight[outLayer_Pos]; + } + inputLayer[inputLayer_Pos].weight_delta[hideLayer_Pos] += sum * hideLayer[hideLayer_Pos].value * (1.0 - hideLayer[hideLayer_Pos].value) + * inputLayer[inputLayer_Pos].value; + } + } + + } + if(error_max < threshold){ + printf("\a Training completed!Total training count:%d, maximum error is:%f\n", trainTime + 1, error_max); + break; + } + for (int inputLayer_Pos = 0; inputLayer_Pos < INNODE; ++inputLayer_Pos) { + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + inputLayer[inputLayer_Pos].weight[hideLayer_Pos] += StudyRate + * inputLayer[inputLayer_Pos].weight_delta[hideLayer_Pos] / + (double) trainSize; + } + } + + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + hideLayer[hideLayer_Pos].bias += StudyRate + * hideLayer[hideLayer_Pos].bias_delta / (double )trainSize; + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + hideLayer[hideLayer_Pos].weight[outLayer_Pos] += StudyRate + * hideLayer[hideLayer_Pos].weight_delta[outLayer_Pos] / (double )trainSize; + } + } + + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + outLayer[outLayer_Pos].bias += StudyRate + * outLayer[outLayer_Pos].bias_delta / (double )trainSize; + } + } + Sample * testSample = getTestData("TestData.txt"); + printf("The predicted results are as follows:\n"); + for (int currentTestSample_Pos = 0; currentTestSample_Pos < testSize; ++currentTestSample_Pos) { + for (int inputLayer_Pos = 0; inputLayer_Pos < INNODE; ++inputLayer_Pos) { + inputLayer[inputLayer_Pos].value = testSample->in[currentTestSample_Pos][inputLayer_Pos]; + } + + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + double sum = 0.0; + for (int inputLayer_Pos = 0; inputLayer_Pos < INNODE; ++inputLayer_Pos) { + sum += inputLayer[inputLayer_Pos].value * inputLayer[inputLayer_Pos].weight[hideLayer_Pos]; + } + sum -= hideLayer[hideLayer_Pos].bias; + hideLayer[hideLayer_Pos].value = sigmoid(sum); + } + + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + double sum = 0.0; + for (int hideLayer_Pos = 0; hideLayer_Pos < HIDENODE; ++hideLayer_Pos) { + sum += hideLayer[hideLayer_Pos].value * hideLayer[hideLayer_Pos].weight[outLayer_Pos]; + } + sum -= outLayer[outLayer_Pos].bias; + outLayer[outLayer_Pos].value = sigmoid(sum); + } + + for (int outLayer_Pos = 0; outLayer_Pos < OUTNODE; ++outLayer_Pos) { + testSample->out[currentTestSample_Pos][outLayer_Pos] = outLayer[outLayer_Pos].value; + } + } + printData(testSample, testSize); + return 0; +}