by ZHAO Jing zj@webturing.com
因为不可以改变,所以不适合大量的拼接(每次拼接都会产生一个副本)
API:length/charAt/indexOf/startsWith/endsWith/contain/split
类型转化: parsXXX
查找/匹配: 多次查找匹配
####成员(方法)变量 member method/field
private: 仅该类自己可见,
default:同一个包类可见
protected:子类可见
public:所有类都可见
静态字段在类加载时初始化,属于整个类(所有成员都共享),用类名引用
成员字段在构造函数调用时初始化,属于对象本身(每一个对象一份),用对象引用
静态方法只要导入了类,都可以调用(静态方法内部只能调用静态方法)
成员方法必须在对象产生后(通常是new)后才可以使用,既可以调用成员方法也可以调用静态方法
类A中必须拥有方法f()的声明,可以是抽象方法
调用子类f还是父类f则会根据最后一次绑定的对象类型而定(多态)
final 定义的变量为常量:Et .final int a=3;后a++则编译错误
如果为引用类型,表示引用关系不会改变(对象本身可以数值变化)
final描述的方法不可以被子类重载
final 描述的类,不可以有子类(称为最终类)
final/abstract永远不会同时修饰一个元素
全部方法都是public abstract的方法,
全部数据都是public static final数据
接口刻画了类的部分特征,比父类更灵活,更抽象,可以当成父类使用
按层次构建类,并解决类重名的问题,都是小写字母如com.qq.view
默认描述符描述的字段/方法,只在同一个包内可以访问
定义在类A内部的类B称为内部类,其名称为A$B.class,为了提高封装性
匿名类:隐式继承/实现一个类(接口)A(一般都重载该类方法),为了提高程序的效率,如比较器Comparator和窗体鼠标消息等
泛型编程 class XXX{}
算法和数据结构的实现
OOP的典范
静态算法(用类调用):Math/Arrays/Collections
对象算法:Random BigInteger BigDecimal
包装器:Integer Long Character
i. 集合迭代器访问方法
ii. Foreach
iii. Get(index)//链表O(n),数组表为O(1)
i. 基于排序树TreeSet:
排序 去重
所有操作原子操作都是lg(N)
ii. 基于哈希表HashSet
去重
所有原子操作 O(1)
i. 基于排序树TreeMap要求键有序
ii. 基于哈系表HashMap 不保证键有序
iii. 迭代键的集合keySet(),valueSet(), EntrySet()
\3. Queue:
i. 字符串统计,键值互转
ii. 利用Map实现电话本操作
iii. 利用Map实现数据库的模拟(登录验证)
iv. 二叉树建模:BinaryTree
v. 图建模:TreeMap<Integer,Vector> graph;
利用向导建立一个安卓项目,并运行
把这个项目用推送到github/gitee上
在这个项目里实现如下功能:做一个对话框显示出今天的日期和时间
用git同步这个项目
Button
TextView
EditText
数据库
SQLiteOpenHelper:抽象类,我们通过继承该类,然后重写数据库创建以及更新的方法, 我们还可以通过该类的对象获得数据库实例,或者关闭数据库!
SQLiteDatabase:数据库访问类:我们可以通过该类的对象来对数据库做一些增删改查的操作
Cursor:游标,有点类似于JDBC里的resultset,结果集!可以简单理解为指向数据库中某 一个记录的指针!
数据库操作:
实现SharedPreference读写
实现Sqlite数据库增删改查
实现一个基础的用户管理系统:登录,注册,修改个人信息
初始化一个git仓库
和远程库同步
Git 全局设置:
git config --global user.name "webturing"
git config --global user.email "zj@webturing.com"
创建 git 仓库:
mkdir Point24
cd Point24
git init
touch README.md
git add README.md
git commit -m "first commit"
git remote add origin https://gitee.com/webturing/Point24.git
git push -u origin master
已有仓库?
cd existing_git_repo
git remote add origin https://gitee.com/webturing/Point24.git
git push -u origin master
难点:
方案:
任何带括号的中缀式总有一个不需要括号的后缀式与其对应
(1+2)* (3+4) => 1 2 + 3 4 + *
枚举a,b,c,d组成的所有的后缀式
运算符种类 4X4X4=64种
运算数的顺序 7!种=5040 //Collections.shuffle 或者DFS来搜
后缀式合法性的判断计算(栈)
后缀式 ==> 中缀式
后缀式合法性的判断计算(栈)
//如果是一个后缀表达式不合法返回-1=ERROR
private static double eval(String[] exp) {
Stack<Double> S = new Stack<Double>();
for (String tok : exp) {
if (isNumber(tok)) {
S.push(Double.parseDouble(tok));
} else {
if(S.size()<2)return ERROR;
double b = S.peek();
S.pop();
double a = S.peek();
S.pop();
double c=0;
switch (tok) {
case "+":
c = a + b;
break;
case "*":
c = a * b;
break;
default:
break;
}
S.push(c);
}
}
return S.size()!=1?ERROR:S.peek();
}
判断一个符号是否是数值//异常处理技术
static boolean isNumber(String tok) {
try {
Double.parseDouble(tok);
return true;
} catch (NumberFormatException e) {
return false;
}
}
方法的委托 delegate
/**
* 随机搜索器的实现v1.0
* 枚举运算符的种类,构造出后缀表达式
* @param arr
* @return
*/
public static List<String> search(int[] arr) {
for (int x = 0; x < 4; x++)
for (int y = 0; y < 4; y++)
for (int z = 0; z < 4; z++) {
List<String> exp = new Vector<>();
exp.add(OPERATORS[x]);
exp.add(OPERATORS[y]);
exp.add(OPERATORS[z]);
for (int i : arr) exp.add(Integer.toString(i));
for (int i = 0; i < MAX_COUNT; i++) {
Collections.shuffle(exp);
double val = PostExpression.eval(exp);
if (val == 24.0) {
return exp;
}
}
}
return null;
}
/**
* 根据后缀表达式生成运算二叉树
* @param exp
* @return
*/
static BinaryTree createBinaryTree(List<String> exp) {
Stack<BinaryTree> S = new Stack<>();
for (String tok : exp) {
if (PostExpression.isNumber(tok)) {
BinaryTree tree = new BinaryTree(tok);
S.push(tree);
} else {
BinaryTree right = S.peek();
S.pop();
BinaryTree left = S.peek();
S.pop();
BinaryTree tree = new BinaryTree(tok, left, right);
S.push(tree);
}
}
return S.peek();
}
void midVisit() {//中序左子树,中序右子树 根节点
System.out.print("(");
if (left != null) {
left.midVisit();
}
System.out.print(root);
if (right != null) {
right.midVisit();
}
System.out.print(")");
}
原模块耦合了System.out会导致在Android不可调用
返回字符串,利用可变字符串StringBuffer来解决递归的性能
void midVisit(StringBuffer buffer) {
buffer.append("(");
if(left!=null){
left.midVisit(buffer);
}
buffer.append(root);
if(right!=null){
right.midVisit(buffer);
}
buffer.append(")");
}
多项式空间 用多重循环嵌套 O(n^k)//P问题
子集空间 O(2^n)//NP问题
全排列空间//NP问题
public class SubSetDFS {//递归程序
static int n = 5;
static int[] book = new int[n];
static void dfs(int k) {
if (k >= n) {
System.out.println(Arrays.toString(book));
return;
}
book[k] = 0;
dfs(k + 1);
book[k] = 1;
dfs(k + 1);
}
public static void main(String[] args) {
dfs(0);
}
}
public class Permutation2DFS { //递归程序
static int n = 4;
static int[] book = new int[n];
static int[] arr = new int[n];
static void dfs(int k) {
if (k >= n) {
System.out.println(Arrays.toString(arr));
return;
}
for (int i = 0; i < n; i++) {
if (book[i] == 1) continue;
arr[k] = i;
book[i] = 1;
dfs(k + 1);
book[i] = 0;
}
}
public static void main(String[] args) {
dfs(0);
}
}
static final int FAC[] = { 1, 1, 2, 6, 24, 120, 720, 5040, 40320, 362880 };
public static int[] codel(int x, int m) {
int[] label = new int[m];
int[] n = new int[m];
int cnt;
for (int i = 0; i < m; i++)
label[i] = 1;
for (int i = 0; i < m; i++) {
cnt = x / FAC[m - 1 - i];
x = x % FAC[m - 1 - i];
for (int j = 0; j < m; j++) {
if (label[j] == 0)
continue;
if (cnt == 0) {
label[j] = 0;
n[i] = j;
break;
}
cnt--;
}
}
return n;
}
public List<String> search(int[] arr) {
//4!*4^3*5=24*64*5=7680 <<7!*64=32w+
for (int cc = 0; cc < FAC[4]; cc++) {
int[] idx = codel(cc, 4);
String a = String.valueOf(arr[idx[0]]);
String b = String.valueOf(arr[idx[1]]);
String c = String.valueOf(arr[idx[2]]);
String d = String.valueOf(arr[idx[3]]);
for (int i = 0; i < 4; i++)
for (int j = 0; j < 4; j++)
for (int k = 0; k < 4; k++) {
String X = OPERATORS[i];
String Y = OPERATORS[j];
String Z = OPERATORS[k];
for (String[] ee : new String[][]{
{a, b, X, c, Y, d, Z},
{a, b, c, X, Y, d, Z},
{a, b, X, c, d, Y, Z},
{a, b, c, X, d, Y, Z},
{a, b, c, d, X, Y, Z},}) {
if (Math.abs(PostExpression.eval(ee) - TARGET) < EPS) {
return Arrays.asList(ee);
}
}
}
}
return null;
}
public Set<List<String>> searchAll(int[] arr) {
Set<List<String>> lists = new HashSet<List<String>>();
for (int cc = 0; cc < FAC[4]; cc++) {
int[] idx = codel(cc, 4);
String a = String.valueOf(arr[idx[0]]);
String b = String.valueOf(arr[idx[1]]);
String c = String.valueOf(arr[idx[2]]);
String d = String.valueOf(arr[idx[3]]);
for (int i = 0; i < 4; i++)
for (int j = 0; j < 4; j++)
for (int k = 0; k < 4; k++) {
String X = OPERATORS[i];
String Y = OPERATORS[j];
String Z = OPERATORS[k];
for (String[] ee : new String[][]{
{a, b, X, c, Y, d, Z},
{a, b, c, X, Y, d, Z},
{a, b, X, c, d, Y, Z},
{a, b, c, X, d, Y, Z},
{a, b, c, d, X, Y, Z},}) {
if (Math.abs(PostExpression.eval(ee) - TARGET) < EPS) {
lists.add(new Vector(Arrays.asList(ee)));
}
}
}
}
return lists;
}
onStop
@Override
protected void onStop() {
super.onStop();
//缓存计算结果 shared-preference
Log.i("point24", "saving preference!!!");
SharedPreferences share = MainActivityProject.this.getSharedPreferences(FILENAME, Activity.MODE_PRIVATE);
SharedPreferences.Editor edit = share.edit();
edit.putString("a", editTextA.getText().toString());
edit.putString("b", editTextB.getText().toString());
edit.putString("c", editTextC.getText().toString());
edit.putString("d", editTextD.getText().toString());
edit.putString("sol", textViewSolution.getText().toString());
edit.commit();// 提交更新
}
//读取shared-preference
Log.i("point24", "reading preference!!!");
SharedPreferences share = super.getSharedPreferences(FILENAME, Activity.MODE_PRIVATE);
editTextA.setText(share.getString("a", "0"));
editTextB.setText(share.getString("b", "0"));
editTextC.setText(share.getString("c", "0"));
editTextD.setText(share.getString("d", "0"));
textViewSolution.setText(share.getString("sol", "计算Ing,请等待"));
递归
static int factorial(int n) {//每次都重复计算
if (n <= 1) return 1;
return factorial(n - 1) * n;
}
静态规划:打表
static int[] F;
static void fill() {
F = new int[13];
F[0] = 1;
for (int i = 1; i < F.length; i++) {
F[i] = F[i - 1] * i;
}
}
记忆化搜索(学习模式)
static int[] F = new int[13];
static int factorial(int n) {//DynamicProgramming
if(F[n]!=0){//查表 O(1)
return F[n];
}
if (n <1) return F[n]=1;//及时存储计算结果
return F[n]=factorial(n - 1) * n;//及时存储计算结果
}
public class DatabaseHelper extends SQLiteOpenHelper{
//带全部参数的构造函数,此构造函数必不可少
public DatabaseHelper(Context context, String name, CursorFactory factory, int version) {
super(context, name, factory, version);
}
@Override
public void onCreate(SQLiteDatabase db) {
//创建数据库sql语句并执行
String sql = "create table tb2(numbers varchar(20),solution varchar(50))";
Log.i("DB","数据表创建成功");
db.execSQL(sql);
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { }
}
DatabaseHelper dbHelper = new DatabaseHelper(MainActivity.this, "test_db", null, 1);
Log.i("DB", "数据库创建成功");
final SQLiteDatabase db = dbHelper.getWritableDatabase();
int[] arr = new int[] { a, b, c, d };
Arrays.sort(arr);
String keys = Arrays.toString(arr);
// 先查询数据库的结果 如果存在直接读取结果
Log.i("DB", "start querying1!");
Cursor cursor = db.query("tb2", new String[] { "numbers","solution" }, null, null, null, null, null);
boolean find = false;
Log.i("DB", "start querying2!");
while (cursor.moveToNext()) {
String numbers = cursor.getString(cursor.getColumnIndex("numbers"));
if (numbers.equals(keys)) {
String solution = cursor.getString(cursor.getColumnIndex("solution"));
textViewResult.setText(solution);
Toast.makeText(MainActivity.this,"读取本地数据库记录",Toast.LENGTH_SHORT).show();
Log.i("DB", "query succesfully!");
find = true;
break;
}
}
// 否则计算后存入数据库
if (!find) {
String answer = Point24.solve(arr);
textViewResult.setText(answer);
ContentValues values = new ContentValues();
Log.i("DB", "start inserting!");
values.put("numbers", keys);
values.put("solution", answer);
// 数据库执行插入命令
db.insert("tb2", null, values);
Log.i("DB", "insert succesfully!");
Toast.makeText(MainActivity.this,"插入数据库成功",Toast.LENGTH_SHORT).show();
}
此处可能存在不合适展示的内容,页面不予展示。您可通过相关编辑功能自查并修改。
如您确认内容无涉及 不当用语 / 纯广告导流 / 暴力 / 低俗色情 / 侵权 / 盗版 / 虚假 / 无价值内容或违法国家有关法律法规的内容,可点击提交进行申诉,我们将尽快为您处理。