手写数字识别(Android版)Android端
手写数字识别(Android版)Android端介绍Android端实现的需求:
调用手机相机拍摄手写好的数字图片
从手机相册中选取手写好的数字图片
将图片上传到服务器
接收服务器返回的结果并显示
这里Android和服务器通信用的是okhttp3协议
问题okhttp3:导入:可以参考文章
若遇到异常:
1No Network Security Config specified, using platform default
解决方法:参考文章
手机存储:若遇到异常:
1java.lang.IllegalArgumentException: Failed to find configured root that contains /storage/emulated/0
在 res/xml/ 下新建一个 file_paths.xml 文件,然后往里写入:
1234<?xml version="1.0" encoding="utf-8"?><paths xmlns:android="ht ...
手写数字识别(Android版)服务端
手写数字识别(Android版)服务端介绍服务端实现的需求:
接收到手机发来的图片并存储到本地
识别本地存储的图片
将识别结果传回手机
使用flask服务器和http协议
实现训练和预测部分和之前的类似,可以参考之前写的文章
网络识别网络可以自定义成识别效果更好的,文件名为:network.py
12345678910111213141516171819import torchimport torch.nn as nn# 自定义手写数字识别网络class net(nn.Module): def __init__(self): super(net, self).__init__() self.Conn_layers = nn.Sequential( nn.Linear(784, 100), nn.Sigmoid(), nn.Linear(100, 10), nn.Sigmoid() ) def forward(self, input): output = self.Conn_layers(inpu ...
二分查找
11.旋转数组的最小数字题目牛客网思路方法:二分法旋转数组将原本有序的数组分成了两部分有序的数组,因为在原始有序数组中,最小的元素一定是在首位,旋转后无序的点就是最小的数字。我们可以将旋转前的前半段命名为A,旋转后的前半段命名为B,旋转数组即将AB变成了BA,我们想知道最小的元素到底在哪里。因为A部分和B部分都是各自有序的,所以我们还是想用分治来试试,每次比较中间值,确认目标值(最小元素)所在的区间。
复杂度分析:
时间复杂度:O(log2n),二分法最坏情况对n取2的对数
空间复杂度:O(1),常数级变量,无额外辅助空间
123456789101112131415161718192021222324252627public class Solution { public int minNumberInRotateArray(int [] array) { int left = 0; int right = array.length - 1; while (left < right) ...
动态规划
10.1斐波那契数列题目牛客网思路方法:迭代相加斐波那契数列初始化第1项与第2项都是1,则根据公式第0项为0,可以按照斐波那契公式累加到第n项。
复杂度分析:
时间复杂度:O(n),其中n为输入的数,n次迭代
空间复杂度:O(1),常数级变量,没有其他额外辅助空间
1234567891011121314151617181920212223public class Solution { public int Fibonacci(int n) { // 从0开始,第0项是0,第一项是1 if (n <= 1) { return n; } int res = 0; int a = 0; int b = 1; // 因n=2时也为1,初始化的时候把a=0,b=1 for (int i = 2;i <= n;i++) { // 第三项开始是前两项的和, ...
堆栈队列
31.栈的压入、弹出序列题目牛客网思路方法:栈用一个栈来模拟两个序列是否符合入栈出栈的次序,对于入栈序列,只要栈为空,序列肯定要依次入栈,当遇到一个元素等于当前的出栈序列的元素,那我们就放弃入栈,让它先出来。
注:重点弄清楚入栈时要满足的条件。
1234567891011121314151617181920212223242526272829303132333435import java.util.Stack;public class Solution { public boolean IsPopOrder(int [] pushA,int [] popA) { // 创建辅助栈 Stack<Integer> s = new Stack<>(); int n = pushA.length; // 初始化入栈的下标 int j = 0; // 遍历出栈的数组 for (int i = 0;i ...
数组与矩阵
3.数组中重复的数字题目牛客网思路
刚开始看到这个题目时第一反应可能是利用两个循环,外循环遍历数组确定要找的重复值,内循环遍历接下来的数组寻找重复值。但这种方法的时间复杂度太大,效率太低。
仔细阅读题目可以看到数字的范围在0~(n-1)之间,也就是说若没有重复的数字,在长度为n的数组里将填充着0~(n-1)范围内所有的数,若有重复的数字,数组中0~(n-1)之间的数肯定填不满。由此可以在外部再创建一个数组,在遍历原数组的同时把原数组上的数字存储到新建数组对应下标当中,也就是新建数组上的数字和其下标的值是相同的。但这样时间复杂度虽然变成了O(n)但是空间复杂度也变成了O(n)。
利用思路2中所分析的特性,不创建新的数组,在原数组中进行数据的交换,具体就是从头开始遍历数组,取下标i,i 上的值为numbers[i],将numbers[i]与数组下标为numbers[i]上的值交换,直到交换到i上的值等于i时进行下一个值遍历。这种方法能够让数组下标和对应的值相等,而且还不用开辟新的数组空间。时间复杂度为O(n),空间复杂度为O(1)。在这里采用思路3最好。
Java12345678910 ...
链表
6.从尾到头打印链表题目牛客网思路这里提供两种解题方法:
创建一个额外的栈,然后从头到尾遍历链表,遍历的时候将遍历到的链表值存入栈中,最后再将栈中元素取出就能完成相反的顺序打印链表。
采用头插法。就是定义一个头结点,然后遍历链表,采用头插法将原链表拆除并从头部逐个插入到新链表中,遍历新链表就能得到相反顺序的元素。这里实现头插法:
Java12345678910111213141516171819202122232425262728293031323334public class Solution { public ArrayList<Integer> printListFromTailToHead (ListNode listNode) { // 初始化头结点和p指针 ListNode head = new ListNode(-1); ListNode p = null; // 遍历原链表并构建新链表 while (listNode != null) { // 头插法构建新链表 p = listNode.next ...
Java实现死锁
java实现死锁
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748public class DeadLockDemo { private static Object resource1 = new Object(); private static Object resource2 = new Object(); public static void main(String[] args) { new Thread(() -> { synchronized (resource1) { System.out.println(Thread.currentThread() + "get resource1"); try { // 线程休眠,保证线 ...
Java实现生产者消费者问题
生产者消费者synchronized版实现
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566public class ProducerAndConsumer { public static void main(String[] args) throws Exception { Resources re = new Resources(); new Thread(() -> { for (int i = 1;i <= 10;i++) { try { // 生产资源 re.produce(); } catch (InterruptedE ...
Java刷题常用方法和功能
用java刷算法题的时候会用到一些常用的方法,这些方法包括字符串、数组、集合的方法。Java获取数组的长度1234567String[][] data = new String[2][5];System.out.println("第一维数组长度: " + data.length);System.out.println("第二维数组长度: " + data[0].length);// 字符数组转成字符串char[] ch = {'a', 'b', 'c'};String str = new String(ch);String类常用方法
int length() 返回字符串长度
char charAt(int index) 返回指定下标位置的字符
char[] toCharArray() 将字符串转换为 ...