个人从php转过来的,编程思想我很容易转变
但是学习java的拦路虎才刚刚开始。
java入门难只有一个原因,也是最大的原因,就是标准太乱。
要达成一个目标,没有一个明确的完整标准。
举个最简单的例子:
aes加密:
import sun.misc.BASE64Decoder;
import sun.misc.BASE64Encoder;
import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
/**
* @description: AES工具类
*/
public class Aes {
/**
* 加密
*
* @param content 加密文本
* @param key 加密密钥,appSecret的前16位
* @param iv 初始化向量,appSecret的后16位
* @return
* @throws Exception
*/
public static String encrypt(String content, String key, String iv) throws Exception {
byte[] raw = key.getBytes();
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding"); //"算法/模式/补码方式"
IvParameterSpec ivParam = new IvParameterSpec(iv.getBytes()); //使用CBC模式,需要一个向量iv,可增加加密算法的强度
cipher.init(Cipher.ENCRYPT_MODE, skeySpec, ivParam);
byte[] encrypted = cipher.doFinal(content.getBytes());
return new BASE64Encoder().encode(encrypted);
}
public static String decrypt(String content, String key, String iv) throws Exception {
byte[] raw = key.getBytes();
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding "); //"算法/模式/补码方式"
IvParameterSpec ivParam = new IvParameterSpec(iv.getBytes()); //使用CBC模式,需要一个向量iv,可增加加密算法的强度
cipher.init(Cipher.DECRYPT_MODE, skeySpec, ivParam);
byte[] encrypted = new BASE64Decoder().decodeBuffer(content); //先用base64解密
byte[] original = cipher.doFinal(encrypted);
return new String(original);
}
和
import org.apache.shiro.codec.Base64;
import org.jeecg.common.util.encryption.EncryptedString;
import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
/**
* AES 加密
*/
public class AesEncryptUtil {
//使用AES-128-CBC加密模式,key需要为16位,key和iv可以相同!
private static String KEY = "xxxxxxxxxxxxxx";
private static String IV = "xxxxxxxxxxxxxx";
/**
* 加密方法
* @param data 要加密的数据
* @param key 加密key
* @param iv 加密iv
* @return 加密的结果
* @throws Exception
*/
public static String encrypt(String data, String key, String iv) throws Exception {
try {
Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");//"算法/模式/补码方式"NoPadding PkcsPadding
int blockSize = cipher.getBlockSize();
byte[] dataBytes = data.getBytes();
int plaintextLength = dataBytes.length;
if (plaintextLength % blockSize != 0) {
plaintextLength = plaintextLength + (blockSize - (plaintextLength % blockSize));
}
byte[] plaintext = new byte[plaintextLength];
System.arraycopy(dataBytes, 0, plaintext, 0, dataBytes.length);
SecretKeySpec keyspec = new SecretKeySpec(key.getBytes(), "AES");
IvParameterSpec ivspec = new IvParameterSpec(iv.getBytes());
cipher.init(Cipher.ENCRYPT_MODE, keyspec, ivspec);
byte[] encrypted = cipher.doFinal(plaintext);
return Base64.encodeToString(encrypted);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
/**
* 解密方法
* @param data 要解密的数据
* @param key 解密key
* @param iv 解密iv
* @return 解密的结果
* @throws Exception
*/
public static String desEncrypt(String data, String key, String iv) throws Exception {
try {
byte[] encrypted1 = Base64.decode(data);
Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");
SecretKeySpec keyspec = new SecretKeySpec(key.getBytes(), "AES");
IvParameterSpec ivspec = new IvParameterSpec(iv.getBytes());
cipher.init(Cipher.DECRYPT_MODE, keyspec, ivspec);
byte[] original = cipher.doFinal(encrypted1);
String originalString = new String(original);
return originalString;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
/**
* 使用默认的key和iv加密
* @param data
* @return
* @throws Exception
*/
public static String encrypt(String data) throws Exception {
return encrypt(data, KEY, IV);
}
/**
* 使用默认的key和iv解密
* @param data
* @return
* @throws Exception
*/
public static String desEncrypt(String data) throws Exception {
return desEncrypt(data, KEY, IV);
}
}
这两个工具类都可以运行,但是运行结果都不一样:
a123456//原文
dBMe38M9dx8tPW0KCzaTqg==//Aes的
s/9NBawovhRHWFDXUGXOtw==//AesEnvryptUtil的
你不得不去深究其中的区别,甚至自己造轮子。
我们作为开发者,不知道也不想知道AES加密的轮子是什么构成,我们就是想简简单单加个密……
再举个例子:POST请求的工具类
import java.io.IOException;
import java.nio.charset.Charset;
import java.security.KeyManagementException;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import javax.net.ssl.SSLContext;
import com.alibaba.fastjson.JSONObject;
import org.apache.http.Consts;
import org.apache.http.HttpEntity;
import org.apache.http.NameValuePair;
import org.apache.http.ParseException;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.config.ConnectionConfig;
import org.apache.http.config.Registry;
import org.apache.http.config.RegistryBuilder;
import org.apache.http.config.SocketConfig;
import org.apache.http.conn.socket.ConnectionSocketFactory;
import org.apache.http.conn.socket.LayeredConnectionSocketFactory;
import org.apache.http.conn.socket.PlainConnectionSocketFactory;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.conn.ssl.SSLContexts;
import org.apache.http.conn.ssl.TrustStrategy;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.apache.http.message.BasicHeader;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.apache.http.protocol.HTTP;
/**
* Post:form-data方式,带header的版本
*/
public class HttpUtils {
public static String defaultEncoding = "UTF-8";
/**
* 发送http post请求,并返回响应实体
*
* @param url 请求地址
* @return url响应实体
*/
public static String postRequest(String url) {
return postRequest(url, null, null);
}
/**
* <p>方法名: postRequest</p>
* <p>描述: 发送httpPost请求</p>
*
* @param url
* @param params
* @return
*/
public static String postRequest(String url, Map<String, Object> params) {
return postRequest(url, null, params);
}
/**
* 发送http post请求,并返回响应实体
*
* @param url 访问的url
* @param headers 请求需要添加的请求头
* @param params 请求参数
* @return
*/
public static String postRequest(String url, Map<String, String> headers,
Map<String, Object> params) {
String result = null;
CloseableHttpClient httpClient = buildHttpClient();
HttpPost httpPost = new HttpPost(url);
if (null != headers && headers.size() > 0) {
for (Entry<String, String> entry : headers.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
httpPost.addHeader(new BasicHeader(key, value));
}
}
if (null != params && params.size() > 0) {
List<NameValuePair> pairList = new ArrayList<NameValuePair>(params.size());
for (Entry<String, Object> entry : params.entrySet()) {
NameValuePair pair = new BasicNameValuePair(entry.getKey(), entry.getValue().toString());
pairList.add(pair);
}
httpPost.setEntity(new UrlEncodedFormEntity(pairList, Charset.forName("utf8")));
}
try {
CloseableHttpResponse response = httpClient.execute(httpPost);
try {
HttpEntity entity = response.getEntity();
if (entity != null) {
result = EntityUtils.toString(entity,
Charset.forName(defaultEncoding));
}
} finally {
response.close();
}
} catch (Exception ex) {
ex.printStackTrace();
} finally {
try {
httpClient.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return result;
}
/**
* 发送http get请求
*
* @param url 请求url
* @return url返回内容
*/
public static String getRequest(String url) {
return getRequest(url, null);
}
/**
* 发送http get请求
*
* @param url 请求的url
* @param params 请求的参数
* @return
*/
public static String getRequest(String url, Map<String, Object> params) {
return getRequest(url, null, params);
}
/**
* 发送http get请求
*
* @param url 请求的url
* @param headersMap 请求头
* @param params 请求的参数
* @return
*/
public static String getRequest(String url, Map<String, String> headersMap, Map<String, Object> params) {
String result = null;
CloseableHttpClient httpClient = buildHttpClient();
try {
String apiUrl = url;
if (null != params && params.size() > 0) {
StringBuffer param = new StringBuffer();
int i = 0;
for (String key : params.keySet()) {
if (i == 0)
param.append("?");
else
param.append("&");
param.append(key).append("=").append(params.get(key));
i++;
}
apiUrl += param;
}
HttpGet httpGet = new HttpGet(apiUrl);
if (null != headersMap && headersMap.size() > 0) {
for (Entry<String, String> entry : headersMap.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
httpGet.addHeader(new BasicHeader(key, value));
}
}
CloseableHttpResponse response = httpClient.execute(httpGet);
try {
HttpEntity entity = response.getEntity();
if (null != entity) {
result = EntityUtils.toString(entity, defaultEncoding);
}
} finally {
response.close();
}
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (ParseException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
httpClient.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return result;
}
/**
* 创建httpclient
*
* @return
*/
public static CloseableHttpClient buildHttpClient() {
try {
RegistryBuilder<ConnectionSocketFactory> builder = RegistryBuilder
.create();
ConnectionSocketFactory factory = new PlainConnectionSocketFactory();
builder.register("http", factory);
KeyStore trustStore = KeyStore.getInstance(KeyStore
.getDefaultType());
SSLContext context = SSLContexts.custom().useTLS()
.loadTrustMaterial(trustStore, new TrustStrategy() {
public boolean isTrusted(X509Certificate[] chain,
String authType) throws CertificateException {
return true;
}
}).build();
LayeredConnectionSocketFactory sslFactory = new SSLConnectionSocketFactory(
context,
SSLConnectionSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
builder.register("https", sslFactory);
Registry<ConnectionSocketFactory> registry = builder.build();
PoolingHttpClientConnectionManager manager = new PoolingHttpClientConnectionManager(
registry);
ConnectionConfig connConfig = ConnectionConfig.custom()
.setCharset(Charset.forName(defaultEncoding)).build();
SocketConfig socketConfig = SocketConfig.custom()
.setSoTimeout(100000).build();
manager.setDefaultConnectionConfig(connConfig);
manager.setDefaultSocketConfig(socketConfig);
return HttpClientBuilder.create().setConnectionManager(manager)
.build();
} catch (KeyStoreException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
return null;
}
}
乍一看没什么,但是请注意这行:
提交的所有内容都变成String型啊~~~~
尼玛放出这个工具类的人,你考虑过提交 数字型 或者 数组型 数据的人的感受了吗?
发起的post请求不被接收,接口一直报参数格式不对这种经历你有吗?
浪费我一个下午就是为了这个傻X工具类。
有人说很多类似的工具类都有大厂做了,比如alibaba等。
但是,作为程序猿,要实现某个功能,最先找的是什么啊?是百度!
没错,这几个傻X工具类就是百度上排行靠前的几个结果里面出来的。
能用不?能用!坑不?真坑!
原因2:框架分的太开,像是缝合怪,大小写十分混乱
java大小写敏感,这是个编程时的便于阅读的利器,也是一把会毁了java的利刃。
controller
service
mapper
entity
这么几个层,
每个层有每个层的规定和实现方法。
就像是各种乱七八糟的东西缝合起来的。
比如:
map的get、put方法和
entity的get、set方法
名字为啥就不能一样呢?
再比如:
mybatis当中必须尽量用大写,有时候驼峰命名法会被转化为下划线导致字段找不到
mybatis plus的很多函数的参数必须用小写,如果用大写会自动转换为小写
请问:哪些函数是mybatis的哪些是plus的呢?需要费多少精力去记?
(可能是我技术不到家,分不开。但是凭什么要让我分开?统一一下不好么?)
原因3:java升级困难,运行起来尾大不掉
像是php,基层默认所有数据类型为String型,这个功能对于初学者很友好。
数据类型转换和内存等问题可以等之后再接触复杂的框架再研究。
但是java不行。java之间数据封装类型和基础类型之间的转换成为了多少程序员的噩梦。
Exception
和try……catch……
成为了业界常态。
而且,在java当中,并发只有3个的时候就能让数据库出现了读取写入顺序错误。(就必须使用事务或者乐观锁)这对于我们这些头发少的还好,对于新手来说简直就是致命的。【想想自己对着教程写一个程序,逻辑都对,但是结果运行总是莫名抽风。】
现在php7+,python标称运行速度是java的多少多少倍,是因为java慢么?不是,而是对java1.7+,1.8+,1.9+ 等等说的。
java没升级了,升级了。为啥没人用?生态?收费(主要是和免费版的反差)?都有。
以上就是我个人认为,为啥java入门难的主要原因,有啥意见,欢迎吐槽。