diff --git a/README.md b/README.md index d9651f8..a5f6c5b 100644 --- a/README.md +++ b/README.md @@ -139,6 +139,10 @@ Frog: 这是人工生命的主体,目前起名叫青蛙(Frog),其实叫什 ![result11](result11_letter_test.gif) 这两个模式的基本原理是基于信号的反向传播,如果一个细胞的两个或多个不同方向同时(或短期内)收到信号,今后只要有一个信号传入,这个细胞将会向其它方向反向发送激活信号。这个模式识别原理非常简单,功能也比较原始,对于变形、扭曲、缩放、缺损的信号识别率很差,但考虑到实现这些功能的复杂性,我近期不打算进一步改进它了,而是打算另起炉灶,用三维空间的细胞分裂+遗传算法的模式,试试看能不能让电脑自动演化出具有简单模式识别功能的模拟生命体,也就是说实现上面发布的任务。 +2021-08-13 演示同时处理多个方向的信号 +位于history\005a1目录下,演示用5个声母和5个韵母的组合来关联到25个图像的识别,这样可以减少声音输入区的数量。它的另一个目的是演示体全息存贮的工作模式可以同时处理多个方向的信号。这个演示分辨率极差,只有约一半的识别率,但我不打算继续改进了。 +![result12](result12_letter_test2.png) + ## 运行方式 | Run 运行history各个子目录下的run.bat批处理文件即可启动运行,history下有多个子目录,按时间和版本号顺序按列,存放着这个项目演化过程中的主要历史版本供演示。 diff --git a/README_ENG.md b/README_ENG.md index ead539b..98be967 100644 --- a/README_ENG.md +++ b/README_ENG.md @@ -100,6 +100,38 @@ The shortcut keys for all brain maps are: T: top view F: front view L: left view ![result9](result9_earthquake.gif) Detailed explanation: The simulation environment of this topic is simplified into two areas on the left and right. When an earthquake occurs (indicated by a red box), all frog energy will be deducted, but only the frog on the left can see the occurrence and stop of the earthquake. The frogs in the right side cannot see the occurrence and stop of the earthquake, but the frogs have articulators and listening organs. If the frog on the left makes a call, it can be heard by the frog on the right. The 6 organs that saw an earthquake occur, saw the earthquake stop, made a call, heard a call, jumped, and landed, corresponded to 6 organs and all evolved accidentally (this does not need to be proved). The purpose of this experiment is to verify Will the frog be forced by the environment to form neural connections among the brain cells corresponding to these six organs? It can be seen that after seeing the earthquake, the frog on the left jumped in the air (indicated by yellow) and made a call, and then the frog on the right also jumped in the air after hearing the call. The frog on the left transmits information to the frog on the right through the call signal, so that the frog on the right avoids its invisible earthquake damage. This is a demonstration of successful group evolution. It proves that even if the nerve cell lines are randomly generated, the biological pronunciation-listening function can be evolved, that is to say, the initial language function can be evolved. +2021-05-15 Demonstration of cell division +This is a small task I posted in the WeChat group. Before I had time to update it here, the pama_1234 in the group was made. The programming speed is not that fast. By the way, he is only a freshman now. After the waves are so experienced. +The task is very simple, just draw a snake like the picture below and win. Require: +1. The small snake has at least 30x30 pixels and has eyes and tongue. Anyway, it looks like a snake at first glance. It is best not to draw feet (Note: So the feet are not drawn, but the corners are drawn). +2. Requires the use of genetic algorithm and split algorithm. Everyone knows about genetic algorithm. Splitting algorithm I only have a general idea right now, which is to imitate cell division to evolve different shapes. Splitting can be to push other cells away, or it can be split only at the edge to reduce the amount of calculation, this is not limited. +3. It is also possible to draw Chinese characters for "snake" and "frog" +The prizes are not planned for the time being, but they will definitely be placed on the project homepage. This task does not seem to have much to do with neural networks, but I think it is possible to use this algorithm to automatically arrange organs, so it still has a certain meaning. Arbitrary complex shapes are generated, and the cell structure of the three-dimensional brain will be possible in the future. Evolved from this task. +Output result ((written by pama_1234): +![result10](result10_drawsnake.gif) +His project is located here: [Cell Painting Snake](https://gitee.com/pama1234/cell-painting-snake), if you are interested in studying the source code, you can take a look. It is based on Processing. +By the way, I also wrote my idea here. I did not study his code carefully, but it is estimated that the idea should be roughly the same: +1. Genes related to shape expression use a polytree structure data structure. The tree structure is a singleton, and only one copy is stored in the memory. After each cell divides, the telomerase is reduced by one, which is equivalent to walking down the tree structure. One level. +2. After each cell is divided, in order to obtain the position of the current cell, but the entire subtree cannot be copied, it is necessary to save a pointer to the current node of the tree, that is, the vertex of the subtree. Nodes that are no longer split may not save node pointers. +3. The gene tree is generally stable, but there is a large probability of small changes, and a small probability of large changes. The changes of the gene tree include the number of repetitions, the direction of bifurcation, and the number of bifurcations. +4. Because it is a polytree, it can start at any point as a fertilized egg to split, and finally can form a specified pattern. + +The task of drawing a snake itself is very simple. It is a task of filling color blocks. It can be done in less than half a second with the drawing brush in the window. The reason why we should treat it as a task and limit the way of cell division. It’s because nature’s solution is not a human-designed algorithm, but only one trick is random cell division, inheritance, and mutation. Now it seems that this division simulation is relatively easy to implement, which roughly explains the various organisms in nature. Reasons for morphogenesis. + +2021-05-15 By the way, release the next development task: frogs eat mushrooms +1. Frogs should distinguish poisonous and non-toxic mushrooms according to different paintings. Mushrooms are represented by randomly generating ten different mushroom patterns. Half of these mushrooms are non-toxic and the other half are poisonous. +2. To use volume holographic storage or surface holographic storage solutions for pattern recognition. For volume holographic storage, please refer to the 005_letter_test example; the surface holographic storage scheme can refer to the laser holographic storage scheme. The difference from volume holography is that the information is stored on a plane instead of in a three-dimensional room. The same point is the use of incident light and outgoing light position information. For storage and reading, the incident light and the outgoing light are reference signals for each other. +3. To proceed under the existing Java project interface, that is to say, to display the virtual environment and mind map, the source file name must be .java suffix. This is different from the cell division demonstration. This task is the main task of the project. +4. Whether mushrooms are poisonous or non-toxic is related to the pattern, but whether they are poisonous or non-toxic must be automatically judged by the frog during the evolution process. A poisonous signal cannot be artificially set to tell the frog (the signal between frogs is not here. limit). The sign of the completion of the mission is that the frogs must be able to evolve to eat all the non-toxic mushrooms in the virtual environment and avoid all the poisonous mushrooms. + +2021-07-04 is still a pattern recognition demonstration +Two new branch directories, history\005a and 005b, were added to demonstrate the use of improved volume holographic storage solutions and surface holographic storage solutions for pattern recognition. It is possible to associate 25 arbitrary graphics with its corresponding sound signal area: +![result11](result11_letter_test.gif) +The basic principle of these two modes is based on the back propagation of signals. If two or more different directions of a cell receive signals at the same time (or within a short period of time), as long as there is one signal coming in in the future, this cell will transmit to other cells. The activation signal is sent in the reverse direction. The principle of pattern recognition is very simple, and the function is relatively primitive. The signal recognition rate for deformation, distortion, scaling, and defect is very poor. However, considering the complexity of implementing these functions, I do not plan to further improve it in the near future, but plan to start anew. , Using the three-dimensional cell division + genetic algorithm model, try to see if the computer can automatically evolve a simulated life form with simple pattern recognition function, that is to say, achieve the tasks posted above. + +2021-08-13 Demonstrate the simultaneous processing of signals in multiple directions +Located in the history\005a1 directory, the demonstration uses a combination of 5 initials and 5 finals to associate with the recognition of 25 images, which can reduce the number of voice input areas. Its other purpose is to demonstrate that the working mode of volume holographic storage can process signals in multiple directions at the same time. The resolution of this demo is very poor, only about half of the recognition rate, but I do not intend to continue to improve. +![result12](result12_letter_test2.png) ## License [Apache 2.0] (http://www.apache.org/licenses/LICENSE-2.0) diff --git a/core/top_down/LICENSE b/core/bottom_up/LICENSE similarity index 100% rename from core/top_down/LICENSE rename to core/bottom_up/LICENSE diff --git a/core/bottom_up/README.md b/core/bottom_up/README.md index 54c9795..cc56603 100644 --- a/core/bottom_up/README.md +++ b/core/bottom_up/README.md @@ -1,4 +1,6 @@ -## core\bottom_up目录简介 -core\top_down目录下的这个项目基于细胞分裂思路,由遗传算法来自动排列脑细胞,并引导脑细胞分裂向体全息存贮方案进化,最终要实现青蛙的模式识别功能,与上下左右运动细胞结合起来,实现吃掉无毒蘑菇,避开有毒蘑菇这个任务。 +## 当前分支简介 + +这个分支基于细胞分裂思路,由遗传算法来自动排列脑细胞,并引导脑细胞分裂向体全息存贮方案进化,以实现模式识别功能,并与上下左右运动细胞结合起来,实现吃掉无毒蘑菇,避开有毒蘑菇这个任务 + +进度:正在编程中,未完成, 本次提交只是清空了多余的文件,保存了最基本的框架,因为是另起炉灶,很多以前的类如organ等都删除了,而是打算要引入基因树的数据结构。 -此目录尚未开始编程 \ No newline at end of file diff --git a/core/top_down/maven_clean.bat b/core/bottom_up/maven_clean.bat similarity index 100% rename from core/top_down/maven_clean.bat rename to core/bottom_up/maven_clean.bat diff --git a/core/top_down/maven_eclipse_clean.bat b/core/bottom_up/maven_eclipse_clean.bat similarity index 100% rename from core/top_down/maven_eclipse_clean.bat rename to core/bottom_up/maven_eclipse_clean.bat diff --git a/core/top_down/maven_eclipse_eclipse.bat b/core/bottom_up/maven_eclipse_eclipse.bat similarity index 100% rename from core/top_down/maven_eclipse_eclipse.bat rename to core/bottom_up/maven_eclipse_eclipse.bat diff --git a/core/bottom_up/pom.xml b/core/bottom_up/pom.xml new file mode 100644 index 0000000..46f10d3 --- /dev/null +++ b/core/bottom_up/pom.xml @@ -0,0 +1,102 @@ + + 4.0.0 + com.gitee.drinkjava2 + frog008 + jar + 1.0 + + frog + 这个分支基于细胞分裂思路,由遗传算法来自动排列脑细胞,并引导脑细胞分裂向体全息存贮方案进化,以实现模式识别功能,并与上下左右运动细胞结合起来,实现吃掉无毒蘑菇,避开有毒蘑菇这个任务 + https://gitee.com/drinkjava2/jsqlbox/frog + + + gitee Issue + https://gitee.com/drinkjava2/jsqlbox/frog/issues + + + + + The Apache Software License, Version 2.0 + http://www.apache.org/licenses/LICENSE-2.0.txt + + + + + + Yong Zhu + yong9981@gmail.com + https://gitee.com/drinkjava2/ + + + + + scm:git@gitee.com:drinkjava2/frog.git + scm:git@gitee.com:drinkjava2/frog.git + git@gitee.com:drinkjava2/frog.git + + + + UTF-8 + UTF-8 + UTF-8 + + 1.8 + 6 + 3.3 + 2.6 + 3.0.0 + 2.7 + 2.19 + 2.6 + 2.4 + 2.10.3 + 1.6 + + + + + + + + + + + + + org.apache.maven.plugins + maven-compiler-plugin + ${version.compiler-plugin} + + ${version.java} + ${version.java} + UTF-8 + + + + org.apache.maven.plugins + maven-jar-plugin + 3.1.2 + + + + true + false + lib/ + com.gitee.drinkjava2.frog.Application + + + + + + + + + + + \ No newline at end of file diff --git a/core/top_down/run.bat b/core/bottom_up/run.bat similarity index 100% rename from core/top_down/run.bat rename to core/bottom_up/run.bat diff --git a/core/top_down/run.sh b/core/bottom_up/run.sh similarity index 100% rename from core/top_down/run.sh rename to core/bottom_up/run.sh diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/Application.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Application.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/Application.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Application.java diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Env.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Env.java new file mode 100644 index 0000000..adac470 --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Env.java @@ -0,0 +1,266 @@ +package com.gitee.drinkjava2.frog; + +import java.awt.Color; +import java.awt.Graphics; +import java.awt.Image; +import java.text.NumberFormat; +import java.util.ArrayList; +import java.util.List; + +import javax.swing.JPanel; + +import com.gitee.drinkjava2.frog.egg.Egg; +import com.gitee.drinkjava2.frog.egg.EggTool; +import com.gitee.drinkjava2.frog.objects.EnvObject; +import com.gitee.drinkjava2.frog.objects.Material; +import com.gitee.drinkjava2.frog.util.RandomUtils; + +/** + * Env is the living space of frog. draw it on JPanel + * + * @author Yong Zhu + * @since 1.0 + */ +@SuppressWarnings("all") +public class Env extends JPanel { + /** Speed of test */ + public static int SHOW_SPEED = 1; // 测试速度,-1000~1000,可调, 数值越小,速度越慢 + + /** Delete eggs at beginning of each run */ + public static final boolean DELETE_EGGS = true;// 每次运行是否先删除保存的蛋 + + public static final int EGG_QTY = 5; // 每轮下n个蛋,可调,只有最优秀的前n个青蛙们才允许下蛋 + + public static final int FROG_PER_EGG = 5; // 每个蛋可以孵出几个青蛙 + + public static final int SCREEN = 1; // 分几屏测完 + + public static final int FROG_PER_SCREEN = EGG_QTY * FROG_PER_EGG / SCREEN; // 每屏上显示几个青蛙,这个数值由上面三个参数计算得来 + + /** Frog's brain size is a 3D array of Cell */ // 脑空间是个三维Cell数组,为节约内存,仅在用到数组元素时才去初始化这维,按需分配内存 + public static final int FROG_BRAIN_XSIZE = 20; // frog的脑在X方向长度 + public static final int FROG_BRAIN_YSIZE = 20; // frog的脑在Y方向长度 + public static final int FROG_BRAIN_ZSIZE = 20; // frog的脑在Z方向长度 + + /** SHOW first frog's brain structure */ + public static boolean SHOW_FIRST_FROG_BRAIN = true; // 是否显示脑图在Env区的右侧 + + /** Draw first frog's brain after some steps */ + public static int DRAW_BRAIN_AFTER_STEPS = 1; // 以此值为间隔动态画出脑图,设为0则关闭这个动态脑图功能,只显示一个静态、不闪烁的脑图 + + /** Environment x width, unit: pixels */ + public static final int ENV_WIDTH = 400; // 虚拟环境的宽度, 可调 + + /** Environment y height, unit: pixels */ + public static final int ENV_HEIGHT = ENV_WIDTH; // 虚拟环境高度, 可调,通常取正方形 + + /** Frog's brain display width on screen, not important */ + public static final int FROG_BRAIN_DISP_WIDTH = 600; // Frog的脑图在屏幕上的显示大小,可调 + + /** Steps of one test round */ + public static final int STEPS_PER_ROUND = 200;// 每轮测试步数,可调 + public static int step;// 当前测试步数 + + public static final int FOOD_QTY = 100; // 食物数量, 可调 + + // 以下是程序内部变量,不要手工修改它们 + public static boolean pause = false; // 暂停按钮按下将暂停测试 + + public static byte[][] bricks = new byte[ENV_WIDTH][ENV_HEIGHT];// 组成环境的材料,见Material.java + + public static List frogs = new ArrayList<>(); // 这里存放所有待测的青蛙,可能分几次测完,由FROG_PER_SCREEN大小来决定 + + public static List eggs = new ArrayList<>(); // 这里存放新建或从磁盘载入上轮下的蛋,每个蛋可能生成几个青蛙, + + public static EnvObject[] things = new EnvObject[]{};// 所有外界物体,如食物、字母测试工具都放在这个things里面 + + static { + System.out.println("脑图快捷键: T:顶视 F:前视 L:左视 R:右视 X:斜视 方向键:剖视 空格:暂停 鼠标:缩放旋转平移"); + if (DELETE_EGGS) { + System.out.println("唵缚悉波罗摩尼莎诃!"); // 杀生前先打印往生咒,见码云issue#IW4H8 + EggTool.deleteEggs(); + } + + } + + public Env() { + super(); + this.setLayout(null);// 空布局 + this.setBounds(1, 1, ENV_WIDTH, ENV_HEIGHT); + } + + public static boolean insideEnv(int x, int y) {// 如果指定点在边界内 + return !(x < 0 || y < 0 || x >= ENV_WIDTH || y >= ENV_HEIGHT); + } + + public static boolean outsideEnv(int x, int y) {// 如果指定点超出边界 + return x < 0 || y < 0 || x >= ENV_WIDTH || y >= ENV_HEIGHT; + } + + public static boolean closeToEdge(Frog f) {// 青蛙靠近边界? 离死不远了 + return f.x < 20 || f.y < 20 || f.x > (Env.ENV_WIDTH - 20) || f.y > (Env.ENV_HEIGHT - 20); + } + + public static boolean foundAnyThing(int x, int y) {// 如果指定点看到任意东西或超出边界 + return x < 0 || y < 0 || x >= ENV_WIDTH || y >= ENV_HEIGHT || Env.bricks[x][y] >= Material.VISIBLE; + } + + public static boolean foundAndAteFood(int x, int y) {// 如果x,y有食物,将其清0,返回true + if (insideEnv(x, y) && Env.bricks[x][y] == Material.FOOD) { + bricks[x][y] = 0; + return true; + } + return false; + } + + private void rebuildFrogs() { + frogs.clear(); + for (int i = 0; i < eggs.size(); i++) {// 创建青蛙,每个蛋生成n个蛙,并随机取一个别的蛋作为精子 + int loop = FROG_PER_EGG; + if (eggs.size() > 20) { // 如果数量多,进行一些优化,让排名靠前的Egg多孵出青蛙 + if (i < FROG_PER_EGG)// 0,1,2,3 + loop = FROG_PER_EGG + 1; + if (i >= (eggs.size() - FROG_PER_EGG)) + loop = FROG_PER_EGG - 1; + } + for (int j = 0; j < loop; j++) { + Egg zygote = new Egg(eggs.get(i), eggs.get(RandomUtils.nextInt(eggs.size()))); + frogs.add(new Frog(RandomUtils.nextInt(ENV_WIDTH), RandomUtils.nextInt(ENV_HEIGHT), zygote)); + } + } + } + + private void drawWorld(Graphics g) { + byte brick; + for (int x = 0; x < ENV_WIDTH; x++) + for (int y = 0; y < ENV_HEIGHT; y++) { + brick = bricks[x][y]; + if (brick != 0) { + g.setColor(Material.color(brick)); + if (brick == Material.FOOD) + g.fillRoundRect(x, y, 4, 4, 2, 2); // show food bigger + else + g.drawLine(x, y, x, y); // only 1 point + } + } + g.setColor(Color.BLACK); + } + + static final NumberFormat format100 = NumberFormat.getPercentInstance(); + static { + format100.setMaximumFractionDigits(2); + } + + private static int foodFoundAmount() {// 统计找食数等 + int leftfood = 0; + for (int x = 0; x < ENV_WIDTH; x++) + for (int y = 0; y < ENV_HEIGHT; y++) + if (bricks[x][y] == Material.FOOD) + leftfood++; + return FOOD_QTY - leftfood; + } + + private String foodFoundCountText() {// 统计找食数等 + int foodFound = foodFoundAmount(); + int maxFound = 0; + for (Frog f : frogs) + if (f.ateFood > maxFound) + maxFound = f.ateFood; + return new StringBuilder("找食率:").append(format100.format(foodFound * 1.00 / FOOD_QTY)).append(", 平均: ").append(foodFound * 1.0f / FROG_PER_SCREEN).append(",最多:").append(maxFound).toString(); + } + + public static void checkIfPause(Frog f) { + if (pause) + do { + if (f != null) { + Application.brainPic.drawBrainPicture(f); + Application.brainPic.requestFocus(); + } + sleep(100); + } while (pause); + } + + public static void sleep(long millis) { + try { + Thread.sleep(millis); + } catch (InterruptedException e) { + e.printStackTrace(); + } + } + + public void run() { + EggTool.loadEggs(); // 从磁盘加载egg,或新建一批egg + Image buffImg = createImage(this.getWidth(), this.getHeight()); + Graphics g = buffImg.getGraphics(); + long time0;// 计时用 + int round = 1; + do { + rebuildFrogs(); + for (int screen = 0; screen < SCREEN; screen++) {// 分屏测试,每屏FROG_PER_SCREEN个蛙 + time0 = System.currentTimeMillis(); + for (EnvObject thing : things) // 创建食物、陷阱等物体 + thing.build(); + boolean allDead = false; + Frog firstFrog = frogs.get(screen * FROG_PER_SCREEN); + checkIfPause(firstFrog); + for (int j = 0; j < FROG_PER_SCREEN; j++) { + Frog f = frogs.get(screen * FROG_PER_SCREEN + j); + f.initFrog(); // 初始化器官延迟到这一步,是因为脑细胞太占内存,而且当前屏测完后会清空 + } + + for (step = 0; step < STEPS_PER_ROUND; step++) { + for (EnvObject thing : things)// 调用食物、陷阱等物体的动作 + thing.active(screen); + if (allDead) + break; // 青蛙全死光了就直接跳到下一轮,以节省时间 + allDead = true; + for (int j = 0; j < FROG_PER_SCREEN; j++) { + Frog f = frogs.get(screen * FROG_PER_SCREEN + j); + if (f.active(this)) + allDead = false; + } + + if (SHOW_SPEED > 0 && step % SHOW_SPEED != 0) // 用画青蛙的方式来拖慢速度 + continue; + + if (SHOW_SPEED <= 1) // 如果speed小于0,人为加入延迟 + sleep(5); + + // 开始画青蛙 + g.setColor(Color.white); + g.fillRect(0, 0, this.getWidth(), this.getHeight()); + g.setColor(Color.BLACK); + drawWorld(g); + for (int j = 0; j < FROG_PER_SCREEN; j++) { + Frog f = frogs.get(screen * FROG_PER_SCREEN + j); + f.show(g); + } + + if (firstFrog.alive) { // 开始显示第一个Frog的动态脑图 + if (SHOW_FIRST_FROG_BRAIN) { + g.setColor(Color.red); + g.drawArc(firstFrog.x - 15, firstFrog.y - 15, 30, 30, 0, 360); + g.setColor(Color.BLACK); + } + if (DRAW_BRAIN_AFTER_STEPS > 0 && step % DRAW_BRAIN_AFTER_STEPS == 0) + Application.brainPic.drawBrainPicture(firstFrog); + } + Graphics g2 = this.getGraphics(); + g2.drawImage(buffImg, 0, 0, this); + } + Application.brainPic.drawBrainPicture(firstFrog); + for (int j = 0; j < FROG_PER_SCREEN; j++) { + Frog f = frogs.get(screen * FROG_PER_SCREEN + j); + f.cells = null; // 清空frog脑细胞所占用的内存 + } + Application.mainFrame.setTitle(new StringBuilder("Round: ").append(round).append(", screen:").append(screen).append(", ").append(foodFoundCountText()).append(", 用时: ") + .append(System.currentTimeMillis() - time0).append("ms").toString()); + for (EnvObject thing : things)// 去除食物、陷阱等物体 + thing.destory(); + } + round++; + EggTool.layEggs(); + } while (true); + } + +} diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Frog.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Frog.java new file mode 100644 index 0000000..7e54207 --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/Frog.java @@ -0,0 +1,124 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog; + +import java.awt.Graphics; +import java.awt.Image; +import java.io.FileInputStream; + +import javax.imageio.ImageIO; + +import com.gitee.drinkjava2.frog.brain.Cell; +import com.gitee.drinkjava2.frog.egg.Egg; +import com.gitee.drinkjava2.frog.objects.Material; + +/** + * Frog's name is Sam, Frog is made up of cells, cells are created by gene tree, gene tree is saved in egg. + * + * 青蛙由细胞组成,细胞的生成由基因树决定,基因树保存在蛋里,蛋最早为空,第一个基因树由随机数产生 + * + * @author Yong Zhu + * @since 1.0 + */ +public class Frog {// 这个项目里大量用到全局public变量而不是私有变量+getter/setter,主要是为了编程方便和简洁,大项目不提倡 + /** brain cells */ + public Cell[][][] cells;// 一开始不要初始化,只在调用getOrCreateCell方法时才初始化相关维以节约内存 + + public int x; // frog在Env中的x坐标 + public int y; // frog在Env中的y坐标 + public long energy = 10000000; // 青蛙的能量为0则死掉 + public boolean alive = true; // 设为false表示青蛙死掉了,将不参与计算和显示,以节省时间 + public int ateFood = 0; + + static Image frogImg; + static { + try { + frogImg = ImageIO.read(new FileInputStream(Application.CLASSPATH + "frog.png")); + } catch (Exception e) { + e.printStackTrace(); + } + } + + public Frog(int x, int y, Egg egg) {// x, y 是虑拟环境的坐标 + this.x = x; + this.y = y; + } + + public void initFrog() {// 仅在测试之前调用这个方法初始化frog以节约内存,测试完成后要清空units释放内存 + try { + cells = new Cell[Env.FROG_BRAIN_XSIZE][][]; // 为了节约内存,先只初始化三维数组的x维,另两维用到时再分配 + } catch (OutOfMemoryError e) { + System.out.println("OutOfMemoryError found for frog, force it die."); + this.alive = false; + return; + } + } + + public boolean active(Env v) {// 这个active方法在每一步循环都会被调用,是脑思考的最小帧 + // 如果能量小于0、出界、与非食物的点重合则判死 + if (!alive || energy < 0 || Env.outsideEnv(x, y) || Env.bricks[x][y] >= Material.KILLFROG) { + energy -= 100; // 死掉的青蛙也要消耗能量,确保淘汰出局 + alive = false; + return false; + } + energy -= 20; + + // 这里是最关键的脑细胞主循环,调用每个细胞的act方法 + for (int i = 0; i < Env.FROG_BRAIN_XSIZE; i++) { + Env.checkIfPause(this); + if (cells[i] != null) + for (int j = 0; j < Env.FROG_BRAIN_YSIZE; j++) + if (cells[i][j] != null) + for (int k = 0; k < Env.FROG_BRAIN_ZSIZE; k++) { + Cell cell = cells[i][j][k]; + if (cell != null) + cell.act(); + } + } + return alive; + } + + public void show(Graphics g) {// 显示青蛙的图象 + if (!alive) + return; + g.drawImage(frogImg, x - 8, y - 8, 16, 16, null); + } + + /** Check if cell exist */ + public Cell getCell(int x, int y, int z) {// 返回指定脑坐标的cell ,如果不存在,返回null + if (cells[x] == null || cells[x][y] == null) + return null; + return cells[x][y][z]; + } + + /** Get a cell in position (x,y,z), if not exist, create a new one */ + public Cell getOrCreateCell(int x, int y, int z) {// 获取指定坐标的Cell,如果为空,则在指定位置新建Cell + if (outBrainBound(x, y, z)) + return null; + if (cells[x] == null) + cells[x] = new Cell[Env.FROG_BRAIN_YSIZE][]; + if (cells[x][y] == null) + cells[x][y] = new Cell[Env.FROG_BRAIN_ZSIZE]; + Cell cell = cells[x][y][z]; + if (cell == null) { + cell = new Cell(x, y, z); + cells[x][y][z] = cell; + } + return cell; + } + + + /** Check if x,y,z out of frog's brain bound */ + public static boolean outBrainBound(int x, int y, int z) {// 检查指定坐标是否超出frog脑空间界限 + return x < 0 || x >= Env.FROG_BRAIN_XSIZE || y < 0 || y >= Env.FROG_BRAIN_YSIZE || z < 0 || z >= Env.FROG_BRAIN_ZSIZE; + } + +} diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java new file mode 100644 index 0000000..f176187 --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java @@ -0,0 +1,319 @@ +package com.gitee.drinkjava2.frog.brain; + +import static java.awt.Color.BLACK; +import static java.awt.Color.RED; +import static java.awt.Color.WHITE; +//import static java.awt.BLUE; +import static java.lang.Math.cos; +import static java.lang.Math.round; +import static java.lang.Math.sin; + +import java.awt.Color; +import java.awt.Graphics; +import java.awt.event.KeyAdapter; +import java.awt.event.KeyEvent; +import java.awt.image.BufferedImage; + +import javax.swing.JPanel; + +import com.gitee.drinkjava2.frog.Application; +import com.gitee.drinkjava2.frog.Env; +import com.gitee.drinkjava2.frog.Frog; + +/** + * BrainPicture show first frog's brain structure, for debug purpose only + * + * 这个类用来画出脑图,这不是一个关键类,对脑的运行逻辑无影响,但有了脑图后可以直观地看出脑的3维结构,进行有针对性的改进 + * 可以用鼠标进行平移、缩放、旋转,以及t、f、l、r,x五个键来选择顶视、前视、左视、右视、斜视这5个方向的视图,以及空格暂停、方向键调整切面 + * 鼠标的动作定义在MouseAction类中。 + * + * @author Yong Zhu + * @since 1.0 + */ +@SuppressWarnings("all") +public class BrainPicture extends JPanel { + private static final float d90 = (float) (Math.PI / 2); + + Color picColor = RED; + int brainDispWidth; // screen display piexls width + float scale; // brain scale + int xOffset = 0; // brain display x offset compare to screen + int yOffset = 0; // brain display y offset compare to screen + float xAngle = d90 * .8f; // brain rotate on x axis + float yAngle = d90 / 4; // brain rotate on y axis + float zAngle = 0;// brain rotate on z axis + int xMask = -1;// x Mask + int yMask = -1;// y Mask + BufferedImage buffImg; + Graphics g; + public KeyAdapter keyAdapter; + + public BrainPicture(int x, int y, float brainWidth, int brainDispWidth) { + super(); + this.setLayout(null);// 空布局 + this.brainDispWidth = brainDispWidth; + scale = 0.5f * brainDispWidth / brainWidth; + this.setBounds(x, y, brainDispWidth + 1, brainDispWidth + 1); + buffImg = new BufferedImage(Env.FROG_BRAIN_DISP_WIDTH, Env.FROG_BRAIN_DISP_WIDTH, BufferedImage.TYPE_INT_RGB); + g = buffImg.getGraphics(); + MouseAction act = new MouseAction(this); + this.addMouseListener(act); // 添加鼠标动作监听 + this.addMouseWheelListener(act);// 添加鼠标滚轮动作监听 + this.addMouseMotionListener(act);// 添加鼠标移动动作监听 + + keyAdapter = new KeyAdapter() {// 处理t,f,l,r,x键盘命令 + public void keyPressed(KeyEvent e) { + switch (e.getKeyCode()){ + case KeyEvent.VK_UP:// Y切面向上 + yMask++; + if (yMask > Env.FROG_BRAIN_YSIZE) + yMask = Env.FROG_BRAIN_YSIZE; + break; + case KeyEvent.VK_DOWN:// Y切面向下 + yMask--; + if (yMask < 0) + yMask = 0; + break; + case KeyEvent.VK_LEFT:// x切面向左 + xMask--; + if (xMask < 0) + xMask = 0; + break; + case KeyEvent.VK_RIGHT:// x切面向右 + xMask++; + if (xMask > Env.FROG_BRAIN_XSIZE) + xMask = Env.FROG_BRAIN_XSIZE; + break; + case ' ':// 暂停及继续 + Application.pauseAction.actionPerformed(null); + break; + case 'T':// 顶视 + xAngle = 0; + yAngle = 0; + zAngle = 0; + break; + case 'F':// 前视 + xAngle = d90; + yAngle = 0; + zAngle = 0; + break; + case 'L':// 左视 + xAngle = d90; + yAngle = d90; + zAngle = 0; + break; + case 'R':// 右视 + xAngle = d90; + yAngle = -d90; + zAngle = 0; + break; + case 'X':// 斜视 + xAngle = d90 * .8f; + yAngle = d90 / 4; + zAngle = 0; + break; + default: + } + } + }; + addKeyListener(keyAdapter); + this.setFocusable(true); + } + + public void drawCuboid(Cuboid c) {// 在脑图上画一个长立方体框架,视角是TopView + float x = c.x; + float y = c.y; + float z = c.z; + float xe = c.xe; + float ye = c.ye; + float ze = c.ze; + + drawLine(x, y, z, x + xe, y, z);// 画立方体的下面边 + drawLine(x + xe, y, z, x + xe, y + ye, z); + drawLine(x + xe, y + ye, z, x, y + ye, z); + drawLine(x, y + ye, z, x, y, z); + + drawLine(x, y, z, x, y, z + ze);// 画立方体的中间边 + drawLine(x + xe, y, z, x + xe, y, z + ze); + drawLine(x + xe, y + ye, z, x + xe, y + ye, z + ze); + drawLine(x, y + ye, z, x, y + ye, z + ze); + + drawLine(x, y, z + ze, x + xe, y, z + ze);// 画立方体的上面边 + drawLine(x + xe, y, z + ze, x + xe, y + ye, z + ze); + drawLine(x + xe, y + ye, z + ze, x, y + ye, z + ze); + drawLine(x, y + ye, z + ze, x, y, z + ze); + } + + /*- + 画线,固定以top视角的角度,所以只需要从x1,y1画一条到x2,y2的直线 + 绕 x 轴旋转 θ + x, y.cosθ-zsinθ, y.sinθ+z.cosθ + + 绕 y 轴旋转 θ + z.sinθ+x.cosθ, y, z.cosθ-x.sinθ + + 绕 z 轴旋转 θ + x.cosθ-y.sinθ, x.sinθ+y.consθ, z + -*/ + public void drawLine(float px1, float py1, float pz1, float px2, float py2, float pz2) { + double x1 = px1 - Env.FROG_BRAIN_XSIZE / 2; + double y1 = -py1 + Env.FROG_BRAIN_YSIZE / 2;// 屏幕的y坐标是反的,显示时要正过来 + double z1 = pz1 - Env.FROG_BRAIN_ZSIZE / 2; + double x2 = px2 - Env.FROG_BRAIN_XSIZE / 2; + double y2 = -py2 + Env.FROG_BRAIN_YSIZE / 2;// 屏幕的y坐标是反的,显示时要正过来 + double z2 = pz2 - Env.FROG_BRAIN_ZSIZE / 2; + x1 = x1 * scale; + y1 = y1 * scale; + z1 = z1 * scale; + x2 = x2 * scale; + y2 = y2 * scale; + z2 = z2 * scale; + double x, y, z; + y = y1 * cos(xAngle) - z1 * sin(xAngle);// 绕x轴转 + z = y1 * sin(xAngle) + z1 * cos(xAngle); + y1 = y; + z1 = z; + + x = z1 * sin(yAngle) + x1 * cos(yAngle);// 绕y轴转 + z = z1 * cos(yAngle) - x1 * sin(yAngle); + x1 = x; + z1 = z; + + x = x1 * cos(zAngle) - y1 * sin(zAngle);// 绕z轴转 + y = x1 * sin(zAngle) + y1 * cos(zAngle); + x1 = x; + y1 = y; + + y = y2 * cos(xAngle) - z2 * sin(xAngle);// 绕x轴转 + z = y2 * sin(xAngle) + z2 * cos(xAngle); + y2 = y; + z2 = z; + + x = z2 * sin(yAngle) + x2 * cos(yAngle);// 绕y轴转 + z = z2 * cos(yAngle) - x2 * sin(yAngle); + x2 = x; + z2 = z; + + x = x2 * cos(zAngle) - y2 * sin(zAngle);// 绕z轴转 + y = x2 * sin(zAngle) + y2 * cos(zAngle); + x2 = x; + y2 = y; + + g.setColor(picColor); + g.drawLine((int) round(x1) + Env.FROG_BRAIN_DISP_WIDTH / 2 + xOffset, (int) round(y1) + Env.FROG_BRAIN_DISP_WIDTH / 2 + yOffset, (int) round(x2) + Env.FROG_BRAIN_DISP_WIDTH / 2 + xOffset, + (int) round(y2) + Env.FROG_BRAIN_DISP_WIDTH / 2 + yOffset); + } + + /** 画出cell的中心点 */ + public void drawCellCenter(float x, float y, float z, float diameter) { + if (x > 0 && (x < xMask || y < yMask)) + return; + drawPoint(x + 0.5f, y + 0.5f, z + 0.5f, (int) Math.max(2, Math.round(scale * diameter))); + } + + /** 画点,固定以top视角的角度,所以只需要在x1,y1位置画一个点 */ + public void drawPoint(float px1, float py1, float pz1, int diameter) { + double x1 = px1 - Env.FROG_BRAIN_XSIZE / 2; + double y1 = -py1 + Env.FROG_BRAIN_YSIZE / 2;// 屏幕的y坐标是反的,显示时要正过来 + double z1 = pz1 - Env.FROG_BRAIN_ZSIZE / 2; + x1 = x1 * scale; + y1 = y1 * scale; + z1 = z1 * scale; + double x, y, z; + y = y1 * cos(xAngle) - z1 * sin(xAngle);// 绕x轴转 + z = y1 * sin(xAngle) + z1 * cos(xAngle); + y1 = y; + z1 = z; + + x = z1 * sin(yAngle) + x1 * cos(yAngle);// 绕y轴转 + z = z1 * cos(yAngle) - x1 * sin(yAngle); + x1 = x; + z1 = z; + + x = x1 * cos(zAngle) - y1 * sin(zAngle);// 绕z轴转 + y = x1 * sin(zAngle) + y1 * cos(zAngle); + x1 = x; + y1 = y; + + g.setColor(picColor); + g.fillOval((int) round(x1) + Env.FROG_BRAIN_DISP_WIDTH / 2 + xOffset, (int) round(y1) + Env.FROG_BRAIN_DISP_WIDTH / 2 + yOffset - diameter / 2, diameter, diameter); + } + + private static Cuboid brain = new Cuboid(0, 0, 0, Env.FROG_BRAIN_XSIZE, Env.FROG_BRAIN_YSIZE, Env.FROG_BRAIN_ZSIZE); + + public void drawBrainPicture(Frog f) {// 在这个方法里进行青蛙三维脑结构的绘制 + if (!f.alive) + return; + if (!Env.SHOW_FIRST_FROG_BRAIN) + return; + g.setColor(WHITE);// 先清空旧图 + g.fillRect(0, 0, brainDispWidth, brainDispWidth); + g.setColor(BLACK); // 画边框 + g.drawRect(0, 0, brainDispWidth, brainDispWidth); + setPicColor(BLACK); + drawCuboid(brain);// 先把脑的框架画出来 + + setPicColor(RED); + drawLine(0, 0, 0, 1, 0, 0); + drawLine(0, 0, 0, 0, 1, 0); + drawLine(0, 0, 0, 0, 0, 1); + + Graphics g2 = this.getGraphics(); // 这两行是将缓存中的图像写到屏幕上 + g2.drawImage(buffImg, 0, 0, this); + + } + + // getters & setters + public float getScale() { + return scale; + } + + public void setScale(float scale) { + this.scale = scale; + } + + public float getxAngle() { + return xAngle; + } + + public void setxAngle(float xAngle) { + this.xAngle = xAngle; + } + + public float getyAngle() { + return yAngle; + } + + public void setyAngle(float yAngle) { + this.yAngle = yAngle; + } + + public float getzAngle() { + return zAngle; + } + + public void setzAngle(float zAngle) { + this.zAngle = zAngle; + } + + public void setPicColor(Color color) { + this.picColor = color; + } + + public int getxOffset() { + return xOffset; + } + + public void setxOffset(int xOffset) { + this.xOffset = xOffset; + } + + public int getyOffset() { + return yOffset; + } + + public void setyOffset(int yOffset) { + this.yOffset = yOffset; + } + +} diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java new file mode 100644 index 0000000..d1f442a --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java @@ -0,0 +1,41 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.brain; + +/** + * Cell is the smallest unit of brain + * Cell是脑的最小单元, cell的行为由它的器官类型决定 + * + +器官位置、方向、厚度、脑细胞分布直径、细胞发散或聚焦角度 +单个细胞方向、能量吸收曲线、能量发送曲线(阀值、是否永久激活、延时发送、脉冲式发送)、发送方向(正、反、双向) +是否是视细胞、动作细胞 +触突(hole)?(固定式触突,或动态生成触突?) + + + * @author Yong Zhu + * @since 1.0 + */ +public class Cell { + public int x; + public int y; + public int z; + + public Cell(int x, int y, int z) { + this.x = x; + this.y = y; + this.z = z; + } + + public void act() { //cell执行行动 + } + +} diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java new file mode 100644 index 0000000..807d75b --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java @@ -0,0 +1,61 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.brain; + +import com.gitee.drinkjava2.frog.Frog; + +/** + * Cuboid represents a rectangular prism 3d zone in brain + * + * Cuboid是一个长方体,通常用来表示脑内器官的形状 + * + * @author Yong Zhu + * @since 2.0.2 + */ +@SuppressWarnings("all") +public class Cuboid implements Shape { + private static final long serialVersionUID = 1L; + + public int x;// x,y,z是长方体的左下角坐标 + public int y; + public int z; + public int xe;// xe,ye,ze分别是长方体三边长 + public int ye; + public int ze; + + public Cuboid() { + // 空构造器不能省 + } + + public Cuboid(int x, int y, int z, int xe, int ye, int ze) {// 用x,y,z,r来构造 + this.x = x; + this.y = y; + this.z = z; + this.xe = xe; + this.ye = ye; + this.ze = ze; + } + + public Cuboid(Cuboid c) {// 用另一个Cuboid来构造 + this.x = c.x; + this.y = c.y; + this.z = c.z; + this.xe = c.xe; + this.ye = c.ye; + this.ze = c.ze; + } + + @Override + public void drawOnBrainPicture(BrainPicture pic) { + pic.drawCuboid(this); + } + +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java new file mode 100644 index 0000000..57270e6 --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java @@ -0,0 +1,26 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.brain; + +import java.io.Serializable; + +/** + * Shape represents a 3d zone in brain + * + * Shape用来表示脑内器官的形状,一个器官只能有一个shape + * + * @author Yong Zhu + * @since 2.0.2 + */ +public interface Shape extends Serializable { + /* Draw self on brain picture */ + public void drawOnBrainPicture(BrainPicture pic); // 把自己在脑图上画出来 +} diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java new file mode 100644 index 0000000..d920c3e --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java @@ -0,0 +1,43 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.egg; + +import java.io.Serializable; + +import com.gitee.drinkjava2.frog.Frog; + +/** + * Egg is the static structure description of frog, can save as file, to build a + * frog, first need build a egg.
+ * + * 蛋存在的目的是为了以最小的字节数串行化存储Frog的基因树,它是Frog的生成算法描述,而不是Frog本身,这样一来Frog就不能"永生"了,因为每一个egg都不等同于 + * 它的母体, 而且每一次测试,除了少量固有反射外,大部分条件反射的建立都必须从头开始训练,类似于人类,无论人类社会有多聪明, 婴儿始终是一张白纸,除了需要花大量的时间从头学习。 + * + * @author Yong Zhu + * @since 1.0 + */ +public class Egg implements Serializable { + private static final long serialVersionUID = 1L; + + public Egg() {// 无中生有,创建一个蛋,先有蛋,后有蛙 + + } + + /** Create egg from frog */ + public Egg(Frog frog) { // 青蛙下蛋,每个青蛙的器官会创建自已的副本或变异,可以是0或多个 + + } + + /** Create a egg by join 2 eggs */ + public Egg(Egg x, Egg y) { //模拟X、Y 染色体合并,两个蛋生成一个新的蛋 + } + +} diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java new file mode 100644 index 0000000..c3d2cca --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java @@ -0,0 +1,107 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.egg; + +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.ObjectInputStream; +import java.io.ObjectOutputStream; +import java.util.Collections; +import java.util.Comparator; +import java.util.List; + +import com.gitee.drinkjava2.frog.Application; +import com.gitee.drinkjava2.frog.Env; +import com.gitee.drinkjava2.frog.Frog; +import com.gitee.drinkjava2.frog.util.FrogFileUtils; + +/** + * EggTool save eggs to disk + * + * @author Yong Zhu + * @since 1.0 + */ +public class EggTool { + + /** + * Frogs which have higher energy lay eggs + * + * 利用Java串行机制存盘。 能量多(也就是吃的更多)的Frog下蛋并存盘, 以进行下一轮测试,能量少的Frog被淘汰,没有下蛋的资格。 + * 用能量的多少来简化生存竟争模拟,也就是说生存是唯一的奖惩机制,每次下蛋数量固定为EGG_QTY个 + */ + public static void layEggs() { + sortFrogsOrderByEnergyDesc(); + + Frog first = Env.frogs.get(0); + Frog last = Env.frogs.get(Env.frogs.size() - 1); + + try { + Env.eggs.clear(); + for (int i = 0; i < Env.EGG_QTY; i++) + Env.eggs.add(new Egg(Env.frogs.get(i))); + FileOutputStream fo = new FileOutputStream(Application.CLASSPATH + "eggs.ser"); + ObjectOutputStream so = new ObjectOutputStream(fo); + so.writeObject(Env.eggs); + so.close(); + System.out.print("Fist frog energy=" + first.energy); + System.out.println(", Last frog energy=" + last.energy); + System.out.println("Saved " + Env.eggs.size() + " eggs to file '" + Application.CLASSPATH + "eggs.ser'"); + } catch (IOException e) { + System.out.println(e); + } + } + + private static void sortFrogsOrderByEnergyDesc() {// 按能量多少给青蛙排序 + Collections.sort(Env.frogs, new Comparator() { + public int compare(Frog a, Frog b) { + if (a.energy > b.energy) + return -1; + else if (a.energy == b.energy) + return 0; + else + return 1; + } + }); + } + + public static void deleteEggs() {//是否每次测试要删除蛋是在Env.DELETE_EGGS设置 + System.out.println("Delete exist egg file: '" + Application.CLASSPATH + "eggs.ser'"); + FrogFileUtils.deleteFile(Application.CLASSPATH + "eggs.ser"); + } + + /** + * 从磁盘读入一批Egg + */ + @SuppressWarnings("unchecked") + public static void loadEggs() { + boolean errorfound = false; + try { + FileInputStream eggsFile = new FileInputStream(Application.CLASSPATH + "eggs.ser"); + ObjectInputStream eggsInputStream = new ObjectInputStream(eggsFile); + Env.eggs = (List) eggsInputStream.readObject(); + System.out.println( + "Loaded " + Env.eggs.size() + " eggs from file '" + Application.CLASSPATH + "eggs.ser" + "'.\n"); + eggsInputStream.close(); + } catch (Exception e) { + errorfound = true; + } + if (errorfound) { + Env.eggs.clear(); + for (int j = 0; j < Env.EGG_QTY; j++) + Env.eggs.add(new Egg()); + System.out.println("Fail to load egg file at path '" + Application.CLASSPATH + "', created " + + Env.eggs.size() + " eggs to do test.\n"); + } + + } + +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java rename to core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java diff --git a/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java new file mode 100644 index 0000000..e3919ce --- /dev/null +++ b/core/bottom_up/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java @@ -0,0 +1,80 @@ +/* Copyright 2018-2020 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.util; + +import java.util.Random; + +/** + * Random Utilities used in this project + * + * 随机数工具,最理想情况下,随机算法和遗传算法是Frog项目中仅有的两个算法。 + * + * @author Yong Zhu + * @since 1.0 + */ +public class RandomUtils { + + private RandomUtils() { + } + + private static final Random rand = new Random(); + + public static int nextInt(int i) {//生成一个整数 + return rand.nextInt(i); + } + + public static float nextFloat() {//生成一个实数 + return rand.nextFloat(); + } + + public static boolean percent(float percent) {// 有百分之percent的机率为true + return rand.nextInt(100) < percent; + } + + + public static int vary(int v, int percet) {//给定一个整数,有百分之percent的机率变异,变异范围由vary方法决定 + if (percent(percet)) + return vary(v); + return v; + } + + public static int vary(int v) {// 随机有大概率小变异,小概率大变异,极小概率极大变异 + if (percent(40)) + v *= .98 + .04 * nextFloat(); // 0.98~1.02 + if (percent(10)) + v *= .95 + .103 * nextFloat(); // 0.95~1.053 + else if (percent(5)) + v *= .08 + 0.45 * nextFloat(); // 0.8~1.25 + else if (percent(1)) + v *= .05 + 1.5 * nextFloat(); // 0.5~2 + return v; + } + + public static float vary(float v, int percet) {//给定一个实数,有百分之percent的机率变异,变异范围由vary方法决定 + if (percent(percet)) + return vary(v); + return v; + } + + public static float vary(float v) {// 随机有大概率小变异,小概率大变异,极小概率极大变异 + if (percent(40)) + v *= .98 + .04 * nextFloat(); // 0.98~1.02 + if (percent(10)) + v *= .95 + .103 * nextFloat(); // 0.95~1.053 + else if (percent(5)) + v *= .08 + 0.45 * nextFloat(); // 0.8~1.25 + else if (percent(1)) + v *= .05 + 1.5 * nextFloat(); // 0.5~2 + return v; + } + + +} diff --git a/core/top_down/README.md b/core/top_down/README.md index e79140d..7953fa2 100644 --- a/core/top_down/README.md +++ b/core/top_down/README.md @@ -1,3 +1,3 @@ -## history\005b_letter_test简介 -005b是基于history\005_letter_test分支基础上,将体全息存贮方案改为面存贮方案的模式识别,这个方案中所有信息是保存在一个平面上。这个方案并不是否定体全息存贮,仅仅只是展示不同的思路。 -本分支依然只是概念演示,图像的扭曲、旋转、缺失等情况的识别暂不考虑。打算这些放在bottom_up细胞分裂模型阶段再做。 +## top_down目录暂时无内容 + +top_down分支存放手工设计的算法,用来验证思路,history目录下的005、005a、005b分支都是属于这一类。目前本目录暂时无内容。人工生命项目着重点是走自底向上的模式(bottom_up),希望能利用电脑的算力自动进化出脑结构。 diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Move2.java b/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Move2.java deleted file mode 100644 index 46e6cdb..0000000 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Move2.java +++ /dev/null @@ -1,36 +0,0 @@ -/* - * Copyright 2018 the original author or authors. - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by - * applicable law or agreed to in writing, software distributed under the - * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS - * OF ANY KIND, either express or implied. See the License for the specific - * language governing permissions and limitations under the License. - */ -package com.gitee.drinkjava2.frog.brain.organ; - -import com.gitee.drinkjava2.frog.Env; -import com.gitee.drinkjava2.frog.brain.Cuboid; -import com.gitee.drinkjava2.frog.brain.Organ; - -/** - * Move is a special organ the action move photon go to next cell - * - * Move这个器官会让Cell中的光子沿着它的运动方向走到下一格 - * - * @author Yong Zhu - */ -public class Move2 extends Organ { - private static final long serialVersionUID = 1L; - - public Move2() { - super(); - this.shape = new Cuboid(11, 0, 0, Env.FROG_BRAIN_XSIZE-11 , Env.FROG_BRAIN_YSIZE, 20); - this.organName = "MOVE2"; - this.type = Organ.MOVE; // MOVE类型的细胞会保持光子的直线运动,并不在细胞上挖洞 - this.allowVary = false;// 不允许变异 - this.allowBorrow = false;// 不允许借出 - } - -} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/MoveDig.java b/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/MoveDig.java deleted file mode 100644 index 598ac2a..0000000 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/MoveDig.java +++ /dev/null @@ -1,48 +0,0 @@ -/* - * Copyright 2018 the original author or authors. - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by - * applicable law or agreed to in writing, software distributed under the - * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS - * OF ANY KIND, either express or implied. See the License for the specific - * language governing permissions and limitations under the License. - */ -package com.gitee.drinkjava2.frog.brain.organ; - -import java.awt.Color; - -import com.gitee.drinkjava2.frog.Env; -import com.gitee.drinkjava2.frog.Frog; -import com.gitee.drinkjava2.frog.brain.BrainPicture; -import com.gitee.drinkjava2.frog.brain.Cuboid; -import com.gitee.drinkjava2.frog.brain.Organ; - -/** - * Move is a special organ the action move photon go to next cell - * - * MOVE_DIG类型的细胞会保持光子直线运动,并在下一个细胞上挖洞 - * - * @author Yong Zhu - */ -public class MoveDig extends Organ { - private static final long serialVersionUID = 1L; - - public MoveDig() { - super(); - this.shape = new Cuboid(9, 0, 0, 2, Env.FROG_BRAIN_YSIZE, Env.FROG_BRAIN_ZSIZE - 2); - this.organName = "MOVE_DIG"; - this.type = Organ.MOVE_DIG; // MOVE_DIG类型的细胞会保持光子直线运动,并在下一个细胞上挖洞 - this.allowVary = false;// 不允许变异 - this.allowBorrow = false;// 不允许借出 - } - - @Override - public void drawOnBrainPicture(Frog f, BrainPicture pic) { // 把器官的轮廓显示在脑图上 - if (!Env.SHOW_FIRST_FROG_BRAIN || !f.alive) // 如果不允许画或青蛙死了,就直接返回 - return; - pic.setPicColor(Color.GREEN); // 缺省是灰色 - shape.drawOnBrainPicture(pic); - } - -} diff --git a/history/005a1_letter_test/LICENSE b/history/005a1_letter_test/LICENSE new file mode 100644 index 0000000..8dada3e --- /dev/null +++ b/history/005a1_letter_test/LICENSE @@ -0,0 +1,201 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "{}" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright {yyyy} {name of copyright owner} + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/history/005a1_letter_test/README.md b/history/005a1_letter_test/README.md new file mode 100644 index 0000000..7afb2ea --- /dev/null +++ b/history/005a1_letter_test/README.md @@ -0,0 +1,4 @@ +## history\005a1_letter_test简介 +这是基于history\005a_letter_test体全息模式识别分支基础上,但是听力部分改为用10个点来代表25个声音,即5个声母 x 5个韵母 =25 个声音。 +因为体全息可以同时处理多个方向的信号,所以可以用声母+韵母同时工作的方式来减少声音信号输入区。 +本分支依然只是概念演示,图像的扭曲、旋转、缺失等情况的识别暂不考虑 diff --git a/history/005a1_letter_test/maven_clean.bat b/history/005a1_letter_test/maven_clean.bat new file mode 100644 index 0000000..2f3d3e5 --- /dev/null +++ b/history/005a1_letter_test/maven_clean.bat @@ -0,0 +1 @@ +mvn clean \ No newline at end of file diff --git a/history/005a1_letter_test/maven_eclipse_clean.bat b/history/005a1_letter_test/maven_eclipse_clean.bat new file mode 100644 index 0000000..a427bd7 --- /dev/null +++ b/history/005a1_letter_test/maven_eclipse_clean.bat @@ -0,0 +1 @@ +mvn eclipse:clean \ No newline at end of file diff --git a/history/005a1_letter_test/maven_eclipse_eclipse.bat b/history/005a1_letter_test/maven_eclipse_eclipse.bat new file mode 100644 index 0000000..99fa0b2 --- /dev/null +++ b/history/005a1_letter_test/maven_eclipse_eclipse.bat @@ -0,0 +1,2 @@ +call mvn eclipse:eclipse +call pause \ No newline at end of file diff --git a/core/top_down/pom.xml b/history/005a1_letter_test/pom.xml similarity index 91% rename from core/top_down/pom.xml rename to history/005a1_letter_test/pom.xml index 498afb0..171d229 100644 --- a/core/top_down/pom.xml +++ b/history/005a1_letter_test/pom.xml @@ -2,12 +2,12 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd"> 4.0.0 com.gitee.drinkjava2 - frog005b + frog005a1 jar 1.0 frog - 005b是基于history\005_letter_test分支基础上,将体全息存贮方案改为面存贮方案的模式识别,这个方案中所有信息是保存在一个平面上。这个方案并不是否定体全息存贮,仅仅只是展示不同的思路。 + 这是基于history\005a_letter_test体全息模式识别分支基础上,但是听力部分改为用10个点来代表25个声音,即5个声母 x 5个韵母 =25 个声音 https://gitee.com/drinkjava2/jsqlbox/frog diff --git a/history/005a1_letter_test/run.bat b/history/005a1_letter_test/run.bat new file mode 100644 index 0000000..0156beb --- /dev/null +++ b/history/005a1_letter_test/run.bat @@ -0,0 +1,3 @@ +call mvn clean compile +cd target\classes +java -classpath ".;*" com.gitee.drinkjava2.frog.Application \ No newline at end of file diff --git a/history/005a1_letter_test/run.sh b/history/005a1_letter_test/run.sh new file mode 100644 index 0000000..836c941 --- /dev/null +++ b/history/005a1_letter_test/run.sh @@ -0,0 +1,2 @@ +mvn clean package +java -jar target/frog-*.jar diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Application.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Application.java new file mode 100644 index 0000000..fcfc94b --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Application.java @@ -0,0 +1,122 @@ +package com.gitee.drinkjava2.frog; + +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.io.File; + +import javax.swing.ButtonGroup; +import javax.swing.JButton; +import javax.swing.JCheckBox; +import javax.swing.JFrame; +import javax.swing.JLabel; +import javax.swing.JRadioButton; +import javax.swing.JSlider; +import javax.swing.event.ChangeEvent; +import javax.swing.event.ChangeListener; + +import com.gitee.drinkjava2.frog.brain.BrainPicture; + +/** + * Application's main method start the program + * + * @author Yong Zhu + * @since 1.0 + */ +@SuppressWarnings("all") +public class Application { + + public static final String CLASSPATH; + + static { + String classpath = new File("").getAbsolutePath(); + int i = classpath.indexOf("\\frog\\"); + if (i > 0) + CLASSPATH = classpath.substring(0, i) + "\\frog\\";// windows + else + CLASSPATH = classpath + "/"; // UNIX + } + + public static JFrame mainFrame = new JFrame(); + public static Env env = new Env(); + public static BrainPicture brainPic = new BrainPicture(Env.ENV_WIDTH + 5, 0, Env.FROG_BRAIN_XSIZE, + Env.FROG_BRAIN_DISP_WIDTH); + public static ActionListener pauseAction; + public static boolean selectFrog = true; + + private static void checkIfShowBrainPicture(JButton button) { + if (Env.SHOW_FIRST_FROG_BRAIN) { + button.setText("Hide brain"); + int y = Env.ENV_HEIGHT + 160; + if (Env.FROG_BRAIN_DISP_WIDTH + 41 > y) + y = Env.FROG_BRAIN_DISP_WIDTH + 41; + mainFrame.setSize(Env.ENV_WIDTH + Env.FROG_BRAIN_DISP_WIDTH + 25, y); + brainPic.requestFocus(); + } else { + button.setText("Show brain"); + mainFrame.setSize(Env.ENV_WIDTH + 20, Env.ENV_HEIGHT + 160); + } + } + + public static void main(String[] args) { + mainFrame.setLayout(null); + mainFrame.setSize(Env.ENV_WIDTH + 20, Env.ENV_HEIGHT + 100); // 窗口大小 + mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // 关闭时退出程序 + mainFrame.add(env); // 添加虚拟环境Panel + mainFrame.add(brainPic); // 添加脑图Panel + + JButton showBrainbutton = new JButton("Show brain");// 按钮,显示或隐藏脑图 + int buttonWidth = 100; + int buttonHeight = 22; + int buttonXpos = Env.ENV_WIDTH / 2 - buttonWidth / 2; + + showBrainbutton.setBounds(buttonXpos, Env.ENV_HEIGHT + 8, buttonWidth, buttonHeight); + ActionListener al = new ActionListener() { + @Override + public void actionPerformed(ActionEvent arg0) {//显示或隐藏脑图 + Env.SHOW_FIRST_FROG_BRAIN = !Env.SHOW_FIRST_FROG_BRAIN; + checkIfShowBrainPicture(showBrainbutton); + } + }; + checkIfShowBrainPicture(showBrainbutton); + showBrainbutton.addActionListener(al); + mainFrame.add(showBrainbutton); + + JButton stopButton = new JButton("Pause");// 暂停或继续按钮 + stopButton.setBounds(buttonXpos, Env.ENV_HEIGHT + 35, buttonWidth, buttonHeight); + pauseAction = new ActionListener() { + @Override + public void actionPerformed(ActionEvent arg0) { + Env.pause = !Env.pause; + if (Env.pause) { + stopButton.setText("Resume"); + } else { + stopButton.setText("Pause"); + brainPic.requestFocus(); + } + } + }; + stopButton.addActionListener(pauseAction); + mainFrame.add(stopButton); + + // 速度条 + final JSlider speedSlider = new JSlider(1, 10, (int) Math.round(Math.sqrt(Env.SHOW_SPEED))); + speedSlider.setBounds(buttonXpos - 50, stopButton.getY() + 25, buttonWidth + 100, buttonHeight); + ChangeListener slideAction = new ChangeListener() { + @Override + public void stateChanged(ChangeEvent e) { + Env.SHOW_SPEED = speedSlider.getValue() * speedSlider.getValue() * speedSlider.getValue(); + brainPic.requestFocus(); + } + }; + speedSlider.addChangeListener(slideAction); + mainFrame.add(speedSlider); + final JLabel label = new JLabel("Speed:"); + label.setBounds(buttonXpos - 90, stopButton.getY() + 23, 100, buttonHeight); + mainFrame.add(label); + + + mainFrame.setVisible(true); + env.run(); + } + +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/Env.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Env.java similarity index 98% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/Env.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Env.java index b3cd9ee..2c3ab7f 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/Env.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Env.java @@ -39,9 +39,9 @@ public class Env extends JPanel { public static final int FROG_PER_SCREEN = EGG_QTY * FROG_PER_EGG / SCREEN; // 每屏上显示几个青蛙,这个数值由上面三个参数计算得来 /** Frog's brain size is a 3D array of Cell */ // 脑空间是个三维Cell数组,为节约内存,仅在用到数组元素时才去初始化这维,按需分配内存 - public static final int FROG_BRAIN_XSIZE = 22; // frog的脑在X方向长度 + public static final int FROG_BRAIN_XSIZE = 18; // frog的脑在X方向长度 public static final int FROG_BRAIN_YSIZE = 20; // frog的脑在Y方向长度 - public static final int FROG_BRAIN_ZSIZE = 27; // frog的脑在Z方向长度 + public static final int FROG_BRAIN_ZSIZE = 17; // frog的脑在Z方向长度 /** SHOW first frog's brain structure */ public static boolean SHOW_FIRST_FROG_BRAIN = true; // 是否显示脑图在Env区的右侧 diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/Frog.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Frog.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/Frog.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/Frog.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java similarity index 97% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java index cab50a7..b5645f6 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/BrainPicture.java @@ -280,10 +280,13 @@ public class BrainPicture extends JPanel { if (cell.hasInput && x == 0) {// 如果在左边,显示黑色大圆 setPicColor(Color.BLACK); drawCellCenter(x, y, z, 0.6f); - } else if (z == Env.FROG_BRAIN_ZSIZE - 1 && cell.hasInput) {// 如果在顶上边,显示兰色大圆 + } else if (z == Env.FROG_BRAIN_ZSIZE - 1 && cell.hasInput) {// 如果在顶上且有输入信号,显示兰色大圆 setPicColor(Color.BLUE); drawCellCenter(x, y, z, 0.6f); - } + } else if (y == 0 && cell.hasInput) {// 如果在前面且有输入信号,显示兰色大圆 + setPicColor(Color.BLUE); + drawCellCenter(x, y, z, 0.6f); + } if (cell.photonQty > 0) {// 如果在内部,只显示有光子的cell setPicColor(ColorUtils.colorByCode(cell.color)); diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Cell.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/CellActions.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/CellActions.java similarity index 60% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/CellActions.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/CellActions.java index e62b0aa..11da0fa 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/CellActions.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/CellActions.java @@ -49,7 +49,26 @@ public class CellActions { for (int orgNo : c.organs) { Organ o = frog.organs.get(orgNo); switch (o.type) { // 添加细胞的行为,这是硬编码 - case Organ.MOVE_DIG: // 如果是MOVE_DIG细胞,它让每个光子穿过这个细胞走到下一格,并在下一个细胞上打出洞来 + case Organ.MOVE: // 如果是MOVE细胞,它的行为是让每个光子穿过这个细胞走到下一格,保持光子沿直线运动 + if (c.x == 0 || c.z == Env.FROG_BRAIN_ZSIZE - 1) {// 但是对于输入区,将删除光子,并合计一共收到多少 + if (c.photonQty > 0) { + c.photonSum += c.photonQty; + c.photons = null; + } + break; + } + if (c.photons != null) { + for (int ii = 0; ii < c.photons.length; ii++) { + Photon p = c.photons[ii]; + if (p == null || p.activeNo == activeNo)// 同一轮新产生的光子或处理过的光子不再走了 + continue; + p.activeNo = activeNo; + c.removePhoton(ii); + frog.addAndWalk(p); // 让光子自已往下走,走到哪就停到哪个细胞里 + } + } + break; + case Organ.MOVE_JELLY: // 如果是MOVE_JELLY细胞,它让每个光子穿过这个细胞走到下一格,并在下一个细胞上打出洞来 if (c.x == 0 || c.z == Env.FROG_BRAIN_ZSIZE - 1) {// 但是对于输入区,将删除光子,并合计一共收到多少 if (c.photonQty > 0) { c.photonSum += c.photonQty; @@ -68,47 +87,37 @@ public class CellActions { } } break; - case Organ.MOVE: // 如果是MOVE细胞,它的行为是让每个光子穿过这个细胞走到下一格,保持光子沿直线运动 - if (c.x == 0 || c.z == Env.FROG_BRAIN_ZSIZE - 1) {// 但是对于输入区,将删除光子,并合计一共收到多少 - if (c.photonQty > 0) { - c.photonSum += c.photonQty; - c.photons = null; - } - break; - } - if (c.photons != null) { - for (int ii = 0; ii < c.photons.length; ii++) { - Photon p = c.photons[ii]; - if (p == null || p.activeNo == activeNo)// 同一轮新产生的光子或处理过的光子不再走了 - continue; - p.activeNo = activeNo; - c.removePhoton(ii); - frog.addAndWalk(p); // 让光子自已往下走,走到哪就停到哪个细胞里 - } - } - break; case Organ.EYE: // 如果是视网膜细胞,它的行为是只要Cell有输入信号,就产生向右的多个光子发散出去,模拟波源 - if (c.hasInput && RandomUtils.percent(100)) {// 随机数的作用是减少光子数,加快速度 -// for (float yy = -0.1f; yy <= 0.1f; yy += 0.15) {// 形成一个扇面向右发送 -// for (float zz = -0.1f; zz <= 0.1f; zz += 0.15) { - Photon p = new Photon(orgNo, o.color, c.x, c.y, c.z, 1.0f, 0, -1.45f); + if (c.hasInput && RandomUtils.percent(40)) {// 随机数的作用是减少光子数,加快速度 + for (float yy = -0.1f; yy <= 0.1f; yy += 0.08) {// 形成一个扇面向右发送 + for (float zz = -0.1f; zz <= 0.1f; zz += 0.08) { + Photon p = new Photon(orgNo, o.color, c.x, c.y, c.z, 1.0f, yy, zz); p.activeNo = activeNo; // 用这个activeNo防止一直被赶着走 frog.addAndWalk(p);// 光子不是直接添加,而是走一格后添加在相邻的细胞上 -// } -// } - } - break; - case Organ.EAR: // 如果是听力细胞,它的行为是将只要Cell有输入信号,就产生向下的多个光子发散出去,模拟波源 - if (c.hasInput && RandomUtils.percent(40)) {// 随机数的作用是减少光子数,加快速度 - float xstart=(-c.x)*0.14f-0.020f; - for (float xx = xstart; xx<0; xx += 0.02) - for (float yy = -2f; yy <= 2f; yy += 0.03) { - Photon p = new Photon(o.organNo, o.color, c.x, c.y, c.z, xx, yy, -1); - p.activeNo = activeNo; - frog.addAndWalk(p);// 光子不是直接添加,而是走一格后添加在相邻的细胞上 } + } } break; + case Organ.TOPEAR: // 如果是顶部声母听力细胞,它的行为是将只要Cell有输入信号,就产生向下的多个光子发散出去,模拟波源 + if (c.hasInput && RandomUtils.percent(40)) {// 随机数的作用是减少光子数,加快速度 + for (float xx=-0.1f; xx<0.1f; xx+=0.04) + for (float yy = -2f; yy <= 2f; yy += 0.03) { + Photon p = new Photon(o.organNo, o.color, c.x, c.y, c.z, xx, yy, -1); + p.activeNo = activeNo; + frog.addAndWalk(p);// 光子不是直接添加,而是走一格后添加在相邻的细胞上 + } + } + break; + case Organ.FRONTEAR: // 如果是面前韵母听力细胞,它的行为是将只要Cell有输入信号,就产生y方向发散光子,模拟波源 + if (c.hasInput && RandomUtils.percent(40)) {// 随机数的作用是减少光子数,加快速度 + for (float xx=-0.1f; xx<0.1f; xx+=0.04) + for (float zz = -2f; zz <= 2f; zz += 0.03) { + Photon p = new Photon(o.organNo, o.color, c.x, c.y, c.z, xx, 1, zz); + p.activeNo = activeNo; + frog.addAndWalk(p);// 光子不是直接添加,而是走一格后添加在相邻的细胞上 + } + } + break; default: break; } diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Cone.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Cone.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Cone.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Cone.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Cuboid.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Hole.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Hole.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Hole.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Hole.java diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java new file mode 100644 index 0000000..ef62cdd --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/MouseAction.java @@ -0,0 +1,106 @@ +package com.gitee.drinkjava2.frog.brain; + +import java.awt.event.MouseEvent; +import java.awt.event.MouseListener; +import java.awt.event.MouseMotionListener; +import java.awt.event.MouseWheelEvent; +import java.awt.event.MouseWheelListener; + +/** + * MouseAction + * + * 这个类用来处理脑图BrainPicture上的鼠标动作,有平移、旋转、缩放三种 + * + * @author Yong Zhu + * @since 2.0.2 + */ +public class MouseAction implements MouseListener, MouseWheelListener, MouseMotionListener { + private BrainPicture brainPic; + private int buttonPressed = 0; + private int x; + private int y; + + public MouseAction(BrainPicture brainPic) { + this.brainPic = brainPic; + } + + @Override + public void mousePressed(MouseEvent e) {// 记录当前鼠标点 + if (e.getButton() == 1)// 旋转 + buttonPressed = 1; + else if (e.getButton() == 2)// 缩放 + buttonPressed = 2; + else + buttonPressed = 0; + x = e.getPoint().x; + y = e.getPoint().y; + } + + @Override + public void mouseReleased(MouseEvent e) { + buttonPressed = 0; + } + + @Override + public void mouseWheelMoved(MouseWheelEvent e) {// 缩放 + if (e.getWheelRotation() < 0) { + brainPic.scale *= 1.1; + brainPic.xOffset *= 1.1; + brainPic.yOffset *= 1.1; + } else { + brainPic.scale /= 1.1; + brainPic.xOffset /= 1.1; + brainPic.yOffset /= 1.1; + } + } + + @Override + public void mouseDragged(MouseEvent e) {// 旋转 + if (buttonPressed == 1) { + if (e.getX() > x && e.getY() > y) + brainPic.zAngle -= .00f; + else if (e.getX() < x && e.getY() < y) + brainPic.zAngle += .00f; + else { + if (e.getX() > x) + brainPic.yAngle += .02f; + if (e.getX() < x) + brainPic.yAngle -= .02f; + if (e.getY() > y) + brainPic.xAngle -= .02f; + if (e.getY() < y) + brainPic.xAngle += .02f; + } + x = e.getX(); + y = e.getY(); + } + if (buttonPressed == 2) {// 平移 + if (e.getX() > x) + brainPic.xOffset += 6; + if (e.getX() < x) + brainPic.xOffset -= 6; + if (e.getY() > y) + brainPic.yOffset += 6; + if (e.getY() < y) + brainPic.yOffset -= 6; + x = e.getX(); + y = e.getY(); + } + } + + @Override + public void mouseClicked(MouseEvent e) {// do nothing + } + + @Override + public void mouseEntered(MouseEvent e) {// do nothing + } + + @Override + public void mouseExited(MouseEvent e) {// do nothing + } + + @Override + public void mouseMoved(MouseEvent e) { // do nothing + } +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Organ.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Organ.java similarity index 95% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Organ.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Organ.java index 42724ca..0f26571 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Organ.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Organ.java @@ -55,9 +55,10 @@ public class Organ implements Serializable, Cloneable {// 因为要保存在蛋 // 以下是各种器官类型,每个神经元都属于一个器官,每个器官都有一个type类型参数 public static final int EMPTY = 0;// 空细胞,不处理光子 public static final int MOVE = 1;// 会让光子沿直线走一格 - public static final int MOVE_DIG = 2;// 会让光子沿直线走一格,并在下一个细胞上打洞 + public static final int MOVE_JELLY = 2;// 会让光子沿直线走一格,并在下一个细胞上打洞 public static final int EYE = 3;// 眼细胞,会根据cell激活度产生发散到各个方向的光子 - public static final int EAR = 4;// 耳细胞,类似眼细胞,不同点是为了简化,脑内听觉区和输入区混用一个区,所以它也可吸收光子,倒过来激活cell + public static final int TOPEAR = 4;// 耳细胞,类似眼细胞,不同点是为了简化,脑内听觉区和输入区混用一个区,所以它也可吸收光子,倒过来激活cell + public static final int FRONTEAR = 8;// 耳细胞,类似眼细胞,不同点是为了简化,脑内听觉区和输入区混用一个区,所以它也可吸收光子,倒过来激活cell public static final int JELLY = 5; // 光子在当前细胞上可以打出洞来 public static final int STATIC = 6; // 只有静态洞的细胞,它忽略动态洞参数 public static final int MIX = 7; // 同时具有静态和动态洞的细胞 diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Photon.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Photon.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Photon.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Photon.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Relation.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Relation.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Relation.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Relation.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/Shape.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Eye.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Eye.java similarity index 98% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Eye.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Eye.java index 9674962..9e67f6c 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Eye.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Eye.java @@ -25,7 +25,7 @@ public class Eye extends Organ {// 眼睛是长方体 private static final long serialVersionUID = 1L; public Eye() { - this.shape = new Cuboid(0, 3, 14, 1, 13, 13); + this.shape = new Cuboid(0, 3, 2, 1, 13, 13); this.type = Organ.EYE; this.organName = "Eye"; this.allowVary = false;// 不允许变异 diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/FrontEar.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/FrontEar.java new file mode 100644 index 0000000..bdbcf8a --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/FrontEar.java @@ -0,0 +1,72 @@ +/* + * Copyright 2018 the original author or authors. + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.brain.organ; + +import com.gitee.drinkjava2.frog.Frog; +import com.gitee.drinkjava2.frog.brain.Cuboid; +import com.gitee.drinkjava2.frog.brain.Organ; +import com.gitee.drinkjava2.frog.util.ColorUtils; + +/** + * Ear can accept sound input + * + * 耳朵的信号输入区能输入多少个信号取决于它的长度,它的每个输入点都与视觉视号正交 + * + * 耳朵的输入区在2021年6月后改只取 0,2,4,6,8处的细胞作为输入点以获取更清晰反向激活信号,这样总共就是5个有效输入点 + * + * 耳朵目前只有一个, 以后可以在侧面再开一个耳朵,就可以达到5x5=25个声音的输入 + * + * 为简单化,耳朵的识别区和输入区重叠,而不是象人脑一样有单独的虚拟声音,将来在信号强度上作区分,直接听到的信号强度大,反向激活后得到的信号弱 + * + * @author Yong Zhu + * @since 2.0.2 + */ +@SuppressWarnings("all") +public class FrontEar extends Organ {// frontEar耳朵位于脑的前侧,也是长方体 + private static final long serialVersionUID = 1L; + + public FrontEar() { + this.shape = new Cuboid(14, 0, 5, 1, 1, 10);// 手工固定耳区的大小 + this.type = Organ.FRONTEAR; + this.organName = "FrontEar"; + this.allowVary = false;// 不允许变异 + this.allowBorrow = false;// 不允许借出 + this.color = ColorUtils.BLUE; + } + + public void hearSound(Frog f, int code) {//code取0~4,分听代表5个听力细胞的位置 + Cuboid c = (Cuboid) this.shape; + int zz = code % 5; + f.getOrCreateCell(c.x , c.y , c.z+zz*2).hasInput = true; //听力细胞间隔一个分布 + } + + public int readcode(Frog f) {//找出收取光子数最多的点 + int temp = -10000; + int code = -1; + Cuboid c = (Cuboid) this.shape; + System.out.print("Ear received photons qty: "); + for (int z = 0; z <= 4; z++) { + int sum = f.getOrCreateCell(c.x, c.y , c.z+z*2).photonSum; + System.out.print(sum + ","); + if (sum > temp) { + code = z; + temp = sum; + } + } + return code; //code表示保存韵母最大激活信号的y方向序号 + } + + /** 给这个耳朵听到一个字母,激活它的听觉输入区, 注意听觉输入区并不等于听觉成像区 */ + public void hearNothing(Frog f) { + f.setCuboidVales((Cuboid) shape, false); + } + +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Move1.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/MoveJelly.java similarity index 76% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Move1.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/MoveJelly.java index db3dd3f..73ad5f5 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Move1.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/MoveJelly.java @@ -21,14 +21,14 @@ import com.gitee.drinkjava2.frog.brain.Organ; * * @author Yong Zhu */ -public class Move1 extends Organ { +public class MoveJelly extends Organ { private static final long serialVersionUID = 1L; - public Move1() { + public MoveJelly() { super(); - this.shape = new Cuboid(0, 0, 0, 9 , Env.FROG_BRAIN_YSIZE, Env.FROG_BRAIN_ZSIZE-1); - this.organName = "MOVE1"; - this.type = Organ.MOVE; // MOVE类型的细胞会保持光子的直线运动,并不在细胞上挖洞 + this.shape = new Cuboid(0, 0, 0, Env.FROG_BRAIN_XSIZE , Env.FROG_BRAIN_YSIZE, Env.FROG_BRAIN_ZSIZE); + this.organName = "MoveJelly"; + this.type = Organ.MOVE_JELLY; // Empty这个器官并不播种cell,它存在的唯一目的只是充当光子媒介,否则光子会一直走下去消失 this.allowVary = false;// 不允许变异 this.allowBorrow = false;// 不允许借出 } diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Ear.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/TopEar.java similarity index 62% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Ear.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/TopEar.java index 8dd0086..24289da 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/brain/organ/Ear.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/brain/organ/TopEar.java @@ -31,13 +31,13 @@ import com.gitee.drinkjava2.frog.util.ColorUtils; * @since 2.0.2 */ @SuppressWarnings("all") -public class Ear extends Organ {// 耳朵位于脑的顶上,也是长方体 +public class TopEar extends Organ {// 耳朵位于脑的顶上,也是长方体 private static final long serialVersionUID = 1L; - public Ear() { - this.shape = new Cuboid(11, 5, 20, 10, 10, 1);// 手工固定耳区的大小 - this.type = Organ.EAR; - this.organName = "Ear"; + public TopEar() { + this.shape = new Cuboid(6, 5, Env.FROG_BRAIN_ZSIZE - 1, 1, 10, 1);// 手工固定耳区的大小 + this.type = Organ.TOPEAR; + this.organName = "TopEar"; this.allowVary = false;// 不允许变异 this.allowBorrow = false;// 不允许借出 this.color = ColorUtils.BLUE; @@ -45,32 +45,29 @@ public class Ear extends Organ {// 耳朵位于脑的顶上,也是长方体 public void hearSound(Frog f, int code) {//code取0~4,分听代表5个听力细胞的位置 Cuboid c = (Cuboid) this.shape; - int x = code / 5; - int y = code % 5; - f.getOrCreateCell(c.x + x * 2, c.y + y * 2, c.z).hasInput = true; //听力细胞间隔一个分布 + int y1 = code / 5; + f.getOrCreateCell(c.x , c.y+y1*2 , c.z).hasInput = true; //听力细胞间隔一个分布 } - public int readcode(Frog f) {//找出收取光子数最多的点 - int temp = -10000; - int code = -1; - Cuboid c = (Cuboid) this.shape; - System.out.print("Ear received photons qty: "); - for (int x = 0; x <=4; x++) - for (int y = 0; y <= 4; y++) { - int sum = f.getOrCreateCell(c.x+x*2, c.y + y * 2, c.z).photonSum; - System.out.print(sum + ","); - if (sum > temp) { - code = x*5 + y; - temp = sum; - } + public int readcode(Frog f) {//找出收取光子数最多的点 + int temp = -10000; + int code = -1; + Cuboid c = (Cuboid) this.shape; + System.out.print("Ear received photons qty: "); + for (int y = 0; y <= 4; y++) { + int sum = f.getOrCreateCell(c.x, c.y + y * 2, c.z).photonSum; + System.out.print(sum + ","); + if (sum > temp) { + code = y; + temp = sum; } - System.out.println(); - return code; - } + } + return code; //code表示保存声母最大激活信号的y方向序号 + } - /** 给这个耳朵听到一个字母,激活它的听觉输入区, 注意听觉输入区并不等于听觉成像区 */ - public void hearNothing(Frog f) { - f.setCuboidVales((Cuboid) shape, false); - } + /** 给这个耳朵听到一个字母,激活它的听觉输入区, 注意听觉输入区并不等于听觉成像区 */ + public void hearNothing(Frog f) { + f.setCuboidVales((Cuboid) shape, false); + } } diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java similarity index 84% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java index cdaaf57..cb14d94 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/egg/Egg.java @@ -16,11 +16,10 @@ import java.util.List; import com.gitee.drinkjava2.frog.Frog; import com.gitee.drinkjava2.frog.brain.Organ; -import com.gitee.drinkjava2.frog.brain.organ.Ear; import com.gitee.drinkjava2.frog.brain.organ.Eye; -import com.gitee.drinkjava2.frog.brain.organ.Move1; -import com.gitee.drinkjava2.frog.brain.organ.Move2; -import com.gitee.drinkjava2.frog.brain.organ.MoveDig; +import com.gitee.drinkjava2.frog.brain.organ.FrontEar; +import com.gitee.drinkjava2.frog.brain.organ.MoveJelly; +import com.gitee.drinkjava2.frog.brain.organ.TopEar; import com.gitee.drinkjava2.frog.util.RandomUtils; /** @@ -39,11 +38,10 @@ public class Egg implements Serializable { public List organs = new ArrayList<>();// NOSONAR public Egg() {// 无中生有,创建一个蛋,先有蛋,后有蛙 - organs.add(new Move1()); // Move即直线移动光子 - organs.add(new Move2()); // Move即直线移动光子 - organs.add(new MoveDig()); // MoveDig即直线移动光子的同时,也在下一个细胞上用光子打出洞来,这个演示里MoveDig是一个平面,也就是说信息只能保存在一个平面上 + organs.add(new MoveJelly()); // MoveJelly即移动光子,也是果冻记忆细胞,本来可以分成两个器官的,图省事 organs.add(new Eye()); // 眼是手工创建的,必有 - organs.add(new Ear()); // 耳是手工创建的,这个是用来测试ABCD字母识别的 + organs.add(new TopEar()); // 耳是手工创建的,这个是用来测试字母识别的, top和front分别代表声母和韵母 + organs.add(new FrontEar()); // 耳是手工创建的,这个是用来测试字母识别的 } /** Create egg from frog */ diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/egg/EggTool.java diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java new file mode 100644 index 0000000..b12f288 --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/EnvObject.java @@ -0,0 +1,26 @@ +/* Copyright 2018-2020 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.objects; + +/** + * EnvObject means some virtual object in Env + * + * @author Yong Zhu + * @since 1.0 + */ +public interface EnvObject { + + public void build(); // 在Env中创建本身物体,指改变Env.bricks数组元素为本身物体的组成材料。只在每屏测试前调用一次 + + public void destory();// 从Env中清除本身物体,只在每屏测试完成后调用一次 + + public void active(int screen); // 每个步长都会调用一次这个方法 +} diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java new file mode 100644 index 0000000..09ea677 --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Food.java @@ -0,0 +1,48 @@ +/* Copyright 2018-2020 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.objects; + +import static com.gitee.drinkjava2.frog.Env.ENV_HEIGHT; +import static com.gitee.drinkjava2.frog.Env.ENV_WIDTH; +import static com.gitee.drinkjava2.frog.Env.FOOD_QTY; +import static com.gitee.drinkjava2.frog.Env.bricks; + +import com.gitee.drinkjava2.frog.util.RandomUtils; + +/** + * Food randomly scatter on Env + * + * @author Yong Zhu + * @since 1.0 + */ +public class Food implements EnvObject { + + @Override + public void build() { + for (int i = 0; i < FOOD_QTY; i++) // 生成食物 + bricks[RandomUtils.nextInt(ENV_WIDTH)][RandomUtils.nextInt(ENV_HEIGHT)] = Material.FOOD; + } + + @Override + public void destory() { + for (int i = 0; i < ENV_WIDTH; i++) {// 清除食物 + for (int j = 0; j < ENV_HEIGHT; j++) + if (bricks[i][j] == Material.FOOD) + bricks[i][j] = 0; + } + } + + @Override + public void active(int screen) { + // Food do not have any active + } + +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/LetterTester.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/LetterTester.java similarity index 82% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/LetterTester.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/LetterTester.java index 2648e61..30639b7 100644 --- a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/LetterTester.java +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/LetterTester.java @@ -13,8 +13,9 @@ package com.gitee.drinkjava2.frog.objects; import com.gitee.drinkjava2.frog.Env; import com.gitee.drinkjava2.frog.Frog; import com.gitee.drinkjava2.frog.brain.BrainPicture; -import com.gitee.drinkjava2.frog.brain.organ.Ear; import com.gitee.drinkjava2.frog.brain.organ.Eye; +import com.gitee.drinkjava2.frog.brain.organ.FrontEar; +import com.gitee.drinkjava2.frog.brain.organ.TopEar; import com.gitee.drinkjava2.frog.util.StringPixelUtils; /** @@ -42,7 +43,8 @@ public class LetterTester implements EnvObject { public void active(int screen) { Frog frog = Env.frogs.get(screen * Env.FROG_PER_SCREEN); // 这个测试只针对每屏的第一只青蛙,因为脑图固定只显示第一只青蛙 Eye eye = frog.findOrganByName("Eye"); - Ear ear = frog.findOrganByName("Ear"); + TopEar topEar = frog.findOrganByName("TopEar"); + FrontEar frontEar = frog.findOrganByName("FrontEar"); int index = Env.step / TIME; if (Env.step % TIME == 0) @@ -50,15 +52,18 @@ public class LetterTester implements EnvObject { if (index < STR.length()) { BrainPicture.setNote("第" + (index + 1) + "个字训练:"+STR.charAt(index)); - ear.hearSound(frog, index); + topEar.hearSound(frog, index); + frontEar.hearSound(frog, index); eye.seeImageWithOffset(frog, StringPixelUtils.getSanserif12Pixels(STR.substring(index, index + 1)),0,0); } else { int index2 = index % STR.length(); BrainPicture.setNote("第" + (index2 + 1) + "个字识别"); eye.seeImageWithOffset(frog, StringPixelUtils.getSanserif12Pixels(STR.substring(index2, index2 + 1)),0,0); if (Env.step % TIME > (TIME - 2)) { - int result = ear.readcode(frog); - System.out.println("Max=" + result+", 即 '"+STR.substring(result, result+1)+"'"); + int c1 = topEar.readcode(frog); + int c2 = frontEar.readcode(frog); + int result = c1*5+c2; + System.out.println("c1="+c1+", c2="+c2+", result=" + result+", 即 '"+STR.substring(result, result+1)+"'"); frog.prepareNewTraining(); } } diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java new file mode 100644 index 0000000..cf6532f --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Material.java @@ -0,0 +1,41 @@ +/* Copyright 2018-2020 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.objects; + +import java.awt.Color; + +/** + * Object means some thing in Env + * + * 用不同的数字常量代表虚拟环境中不同的组成材料,0为空,小于10的不可见,大于20的将杀死在同一位置出现的青蛙,例如砖头和青蛙不可以重叠出现在同一位置 + * + * @author Yong Zhu + * @since 1.0 + */ +public class Material { + public static final byte NO = 0; // nothing + public static final byte SEESAW_BASE = 1; // 1~9 is invisible to frog + + public static final byte VISIBLE = 10; // if>=10 will visible to frog + public static final byte FOOD = VISIBLE + 1; + public static final byte SEESAW = VISIBLE + 2; + + public static final byte KILLFROG = 20; // if>=20 will kill frog + public static final byte BRICK = KILLFROG + 1;// brick will kill frog + public static final byte TRAP = KILLFROG + 2; // trap will kill frog + + public static Color color(byte material) { + if (material == TRAP) + return Color.LIGHT_GRAY; + else + return Color.BLACK; + } +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/SeeSaw.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/SeeSaw.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/SeeSaw.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/SeeSaw.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/Trap.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Trap.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/objects/Trap.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/objects/Trap.java diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java new file mode 100644 index 0000000..aa944ac --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/ColorUtils.java @@ -0,0 +1,70 @@ +/* Copyright 2018-2020 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.util; + +import java.awt.Color; + +/** + * Color Utilities used in this project + * + * @author Yong Zhu + * @since 1.0 + */ +public class ColorUtils { + public static final int RED = 0; + public static final int ORANGE = 1; + public static final int YELLOW = 2; + public static final int GREEN = 3; + public static final int CYAN = 4; + public static final int BLUE = 5; + public static final int MAGENTA = 6; + public static final int GRAY = 7; + + private static final Color[] rainbow = new Color[] { Color.RED, Color.ORANGE, Color.YELLOW, Color.GREEN, Color.CYAN, + Color.BLUE, Color.MAGENTA,Color.GRAY }; + + private static int nextColor = 0; + + private ColorUtils() {// default private constr + } + + public static int nextColorCode() { + return nextColor++; + } + + public static Color nextRainbowColor() {// 返回下一个彩虹色 + if (nextColor == rainbow.length) + nextColor = 0; + return rainbow[nextColor++]; + } + + public static Color colorByCode(int i) {// 数值取模后返回一个固定彩虹色 + return rainbow[i % rainbow.length]; + } + + public static Color rainbowColor(float i) { // 根据数值大小范围,在8种彩虹色中取值 + if (i == 0) + return Color.BLACK; + if (i == 1) + return Color.RED; + if (i <= 3) + return Color.ORANGE; + if (i <= 10) + return Color.YELLOW; + if (i <= 20) + return Color.GREEN; + if (i <= 50) + return Color.CYAN; + if (i <= 100) + return Color.BLUE; + return Color.MAGENTA; + } +} diff --git a/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java new file mode 100644 index 0000000..708c99f --- /dev/null +++ b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/FrogFileUtils.java @@ -0,0 +1,141 @@ +/* Copyright 2018-2020 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by + * applicable law or agreed to in writing, software distributed under the + * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + * OF ANY KIND, either express or implied. See the License for the specific + * language governing permissions and limitations under the License. + */ +package com.gitee.drinkjava2.frog.util; + +import java.io.ByteArrayOutputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.InputStream; + +/** + * File Utilities used in this project + * + * @author Yong Zhu + * @since 1.0 + */ +public class FrogFileUtils { + + private FrogFileUtils() { + // default constructor + } + + public static boolean deleteFile(String fileFullPath) { + File file = new File(fileFullPath); + return file.delete(); // NOSONAR + } + + public static void writeFile(String fileFullPath, byte[] byteArry) { + File file = new File(fileFullPath); + if (!file.getParentFile().exists()) + file.getParentFile().mkdirs(); + FileOutputStream fos = null; + try { + fos = new FileOutputStream(file); + fos.write(byteArry); + fos.close(); + } catch (Exception e) { + e.printStackTrace(); + } finally { + if (fos != null) { + try { + try { + fos.flush(); + } catch (Exception e) { + } + fos.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + } + + public static void writeFile(String fileFullPath, String text, String encoding) { + File file = new File(fileFullPath); + if (!file.getParentFile().exists()) + file.getParentFile().mkdirs(); + FileOutputStream fos = null; + try { + fos = new FileOutputStream(file); + byte[] bytes; + bytes = text.getBytes(encoding); + fos.write(bytes); + fos.close(); + } catch (Exception e) { + e.printStackTrace(); + } finally { + if (fos != null) { + try { + try { + fos.flush(); + } catch (Exception e) { + } + fos.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + } + + public static String readFile(String fileFullPath, String encoding) { + InputStream inputStream; + try { + inputStream = new FileInputStream(new File(fileFullPath)); + } catch (FileNotFoundException e1) { + return null; + } + try { + ByteArrayOutputStream result = new ByteArrayOutputStream(); + byte[] buffer = new byte[1024]; + int length; + while ((length = inputStream.read(buffer)) != -1) + result.write(buffer, 0, length); + String string = result.toString(encoding); + return string; + } catch (IOException e) { + e.printStackTrace(); + return null; + } finally { + try { + inputStream.close(); + } catch (IOException e) { + } + } + } + + public static void appendFile(String fileName, String content) { + FileOutputStream fos = null; + try { + fos = new FileOutputStream(fileName, true); + fos.write(content.getBytes()); + fos.write("\r\n".getBytes()); + } catch (IOException e) { + e.printStackTrace(); + } finally { + if (fos != null) { + try { + try { + fos.flush(); + } catch (Exception e) { + } + fos.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + } + +} diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/PixelsUtils.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/PixelsUtils.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/PixelsUtils.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/PixelsUtils.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/RandomUtils.java diff --git a/core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/StringPixelUtils.java b/history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/StringPixelUtils.java similarity index 100% rename from core/top_down/src/main/java/com/gitee/drinkjava2/frog/util/StringPixelUtils.java rename to history/005a1_letter_test/src/main/java/com/gitee/drinkjava2/frog/util/StringPixelUtils.java diff --git a/result12_letter_test2.png b/result12_letter_test2.png new file mode 100644 index 0000000..9ef992f Binary files /dev/null and b/result12_letter_test2.png differ diff --git a/版本提交记录.md b/版本提交记录.md index d0cb1f7..b31bcdb 100644 --- a/版本提交记录.md +++ b/版本提交记录.md @@ -214,4 +214,13 @@ T:顶视 F:前视 L:左视 R:右视 X:斜视 方向键:剖视 空格: 2021-07-04 依然是模式识别演示 新增history\005a和005b两个分支目录,分别演示利用改进版的体全息存贮方案和面全息存贮方案来进行模式识别。可以做到将25个任意图形和它对应的声音信号区关联起来。这两个模式的基本原理是基于信号的反向传播,如果一个细胞的两个或多个不同方向同时(或短期内)收到信号,今后只要有一个信号传入,这个细胞将会向其它方向反向发送激活信号。这个模式识别原理非常简单,功能也比较原始,对于变形、扭曲、缩放、缺损的信号识别率很差,但我近期不打算进一步改进它了,而是打算另起炉灶,用三维空间的细胞分裂+遗传算法的模式,试试看能不能让电脑自动演化出具有模式识别功能的模拟生命体,也就是说实现上面发布的任务。 -![result11](result11_letter_test.gif) \ No newline at end of file +![result11](result11_letter_test.gif) + +2021-07-04 依然是模式识别演示 +新增history\005a和005b两个分支目录,分别演示利用改进版的体全息存贮方案和面全息存贮方案来进行模式识别。可以做到将25个任意图形和它对应的声音信号区关联起来: +![result11](result11_letter_test.gif) +这两个模式的基本原理是基于信号的反向传播,如果一个细胞的两个或多个不同方向同时(或短期内)收到信号,今后只要有一个信号传入,这个细胞将会向其它方向反向发送激活信号。这个模式识别原理非常简单,功能也比较原始,对于变形、扭曲、缩放、缺损的信号识别率很差,但考虑到实现这些功能的复杂性,我近期不打算进一步改进它了,而是打算另起炉灶,用三维空间的细胞分裂+遗传算法的模式,试试看能不能让电脑自动演化出具有简单模式识别功能的模拟生命体,也就是说实现上面发布的任务。 + +2021-08-13 演示同时处理多个方向的信号 +位于history\005a1目录下,演示用5个声母和5个韵母的组合来关联到25个图像的识别,这样可以减少声音输入区的数量。它的另一个目的是演示体全息存贮的工作模式可以同时处理多个方向的信号。这个演示分辨率极差,只有约一半的识别率,但我不打算继续改进了。 +![result12](result12_letter_test2.png)