本文代码详见:https://github.com/honghailiang/RetrofitUpLoadImage

一、再次膜拜下Retrofit

Retrofit不管从性能还是使用方便性上都非常屌!!!

,本文不去介绍其运作原理(尽管非常想搞明确)。后面会出专题文章解析Retrofit的内部原理;本文仅仅是从使用上解析Retrofit实现多图片/文件、图文上传的功能。文件上传相关可參考Multipart/form-data文件上传简单介绍Apache FileUpload文件上传功能

二、概念介绍

1)注解@Multipart

从字面上理解就是与多媒体文件相关的,没错,图片、文件等的上传都要用到该注解,当中每一个部分须要使用@Part来注解。

。看其凝视

/**
* Denotes that the request body is multi-part. Parts should be declared as parameters and
* annotated with {@link Part @Part}.
*/

2)注解@PartMap

当然能够理解为使用@PartMap凝视。传递多个Part,以实现多文件上传。

凝视

/**
* Denotes name and value parts of a multi-part request.
* <p>
* Values of the map on which this annotation exists will be processed in one of two ways:
* <ul>
* <li>If the type is {@link okhttp3.RequestBody RequestBody} the value will be used
* directly with its content type.</li>
* <li>Other object types will be converted to an appropriate representation by using
* {@linkplain Converter a converter}.</li>
* </ul>
* <p>
* <pre><code>
* @Multipart
* @POST("/upload")
* Call<ResponseBody> upload(
* @Part("file") RequestBody file,
* @PartMap Map<String, RequestBody> params);
* </code></pre>
* <p>
* A {@code null} value for the map, as a key, or as a value is not allowed.
*
* @see Multipart
* @see Part
*/

3)RequestBody

从上面凝视中就能够看到參数类型是RequestBody,其就是请求体。

文件上传就须要參数为RequestBody。官方使用说明例如以下http://square.github.io/retrofit/

Multipart parts use one of Retrofit's converters or they can implement RequestBody to handle their own serialization.

四、基本实现

了解了以上概念,以下就一一实现

1)接口定义

public interface IHttpService {
@Multipart
@POST("file/upLoad.do")
Call<BaseBean> upLoadAgree(@PartMap Map<String, RequestBody>params);
}

BaseBean是依据服务端返回数据进行定义的。这个使用时能够依据自有Server定义。

2)Retrofit实现

/**
* Created by DELL on 2017/3/16.
* 上传文件用(包括图片)
*/ public class RetrofitHttpUpLoad {
/**
* 超时时间60s
*/
private static final long DEFAULT_TIMEOUT = 60;
private volatile static RetrofitHttpUpLoad mInstance;
public Retrofit mRetrofit;
public IHttpService mHttpService;
private static Map<String, RequestBody> params; private RetrofitHttpUpLoad() {
mRetrofit = new Retrofit.Builder()
.baseUrl(UrlConfig.ROOT_URL)
.client(genericClient())
.addConverterFactory(GsonConverterFactory.create())
.build();
mHttpService = mRetrofit.create(IHttpService.class);
} public static RetrofitHttpUpLoad getInstance() {
if (mInstance == null) {
synchronized (RetrofitHttpUpLoad.class) {
if (mInstance == null)
mInstance = new RetrofitHttpUpLoad();
params = new HashMap<String, RequestBody>();
}
}
return mInstance;
} /**
* 加入统一超时时间,http日志打印
*
* @return
*/
private OkHttpClient genericClient() {
HttpLoggingInterceptor logging = new HttpLoggingInterceptor();
logging.setLevel(HttpLoggingInterceptor.Level.BODY);
OkHttpClient httpClient = new OkHttpClient.Builder()
.addInterceptor(logging)
.connectTimeout(DEFAULT_TIMEOUT, TimeUnit.SECONDS)
.writeTimeout(DEFAULT_TIMEOUT, TimeUnit.SECONDS)
.readTimeout(DEFAULT_TIMEOUT, TimeUnit.SECONDS)
.build();
return httpClient;
} /**
* 将call加入队列并实现回调
*
* @param call 调入的call
* @param retrofitCallBack 回调
* @param method 调用方法标志。回调用
* @param <T> 泛型參数
*/
public <T> void addToEnqueue(Call<T> call, final RetrofitCallBack retrofitCallBack, final int method) {
final Context context = MyApplication.getContext();
call.enqueue(new Callback<T>() {
@Override
public void onResponse(Call<T> call, Response<T> response) {
LogUtil.d("retrofit back code ====" + response.code());
if (null != response.body()) {
if (response.code() == 200) {
LogUtil.d("retrofit back body ====" + new Gson().toJson(response.body()));
retrofitCallBack.onResponse(response, method);
} else {
LogUtil.d("toEnqueue, onResponse Fail:" + response.code());
ToastUtil.makeShortText(context, "网络连接错误" + response.code());
retrofitCallBack.onFailure(response, method);
}
} else {
LogUtil.d("toEnqueue, onResponse Fail m:" + response.message());
ToastUtil.makeShortText(context, "网络连接错误" + response.message());
retrofitCallBack.onFailure(response, method);
}
} @Override
public void onFailure(Call<T> call, Throwable t) {
LogUtil.d("toEnqueue, onResponse Fail unKnown:" + t.getMessage());
t.printStackTrace();
ToastUtil.makeShortText(context, "网络连接错误" + t.getMessage());
retrofitCallBack.onFailure(null, method);
}
});
} /**
* 加入參数
* 依据传进来的Object对象来推断是String还是File类型的參数
*/
public RetrofitHttpUpLoad addParameter(String key, Object o) { if (o instanceof String) {
RequestBody body = RequestBody.create(MediaType.parse("text/plain;charset=UTF-8"), (String) o);
params.put(key, body);
} else if (o instanceof File) {
RequestBody body = RequestBody.create(MediaType.parse("multipart/form-data;charset=UTF-8"), (File) o);
params.put(key + "\"; filename=\"" + ((File) o).getName() + "", body);
}
return this;
} /**
* 构建RequestBody
*/
public Map<String, RequestBody> bulider() { return params;
} public void clear(){
params.clear();
}
}

当中定义了Retrofit实例、还用拦截器定义了统一的超时时间和日志打印;将call加入队列并实现回调。

最重要的就是加入參数:

 /**
* 加入參数
* 依据传进来的Object对象来推断是String还是File类型的參数
*/
public RetrofitHttpUpLoad addParameter(String key, Object o) { if (o instanceof String) {
RequestBody body = RequestBody.create(MediaType.parse("text/plain;charset=UTF-8"), (String) o);
params.put(key, body);
} else if (o instanceof File) {
RequestBody body = RequestBody.create(MediaType.parse("multipart/form-data;charset=UTF-8"), (File) o);
params.put(key + "\"; filename=\"" + ((File) o).getName() + "", body);
}
return this;
}

这里就是依据传入的參数,返回不同的RequestBody, 注意文件的key值。

3)使用

private void upLoadAgree() {
showWaitDialog();
RetrofitHttpUpLoad retrofitHttpUpLoad = RetrofitHttpUpLoad.getInstance();
retrofitHttpUpLoad.clear();
if (!StringUtil.isEmpty(pathImage[0])){
retrofitHttpUpLoad = retrofitHttpUpLoad.addParameter("pic1",new File(pathImage[0]));
}
if (!StringUtil.isEmpty(pathImage[1])){
retrofitHttpUpLoad = retrofitHttpUpLoad.addParameter("pic2", new File(pathImage[1]));
}
if (!StringUtil.isEmpty(pathImage[2])){
retrofitHttpUpLoad = retrofitHttpUpLoad.addParameter("zip", new File(pathImage[2]));
} Map<String, RequestBody> params = retrofitHttpUpLoad
.addParameter("status", "4")
.addParameter("pickupId", tv_orderquality_pid.getText().toString())
.addParameter("cause", reason)
.addParameter("connectname", et_orderquality_lxrname.getText().toString())
.addParameter("connectphone", et_orderquality_lxrphone.getText().toString())
.addParameter("details", et_orderquality_xqms.getText().toString())
.bulider();
retrofitHttpUpLoad.addToEnqueue(retrofitHttpUpLoad.mHttpService.upLoadAgree(params),
this, HttpStaticApi.HTTP_UPLOADAGREE);
}

须要注意的是要对图片及文件路径进行判空操作,否则会报异常W/System.err: java.io.FileNotFoundException: /: open failed: EISDIR (Is a directory)

五、报文日志

当中图片报文有省略

D/OkHttp: --> POST http://192.168.xxx.xxx:8880/xxx/nocheck/file/agree.do http/1.1
D/OkHttp: Content-Type: multipart/form-data; boundary=f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Length: 300580
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="pic2"; filename="90079.jpg"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: multipart/form-data;charset=UTF-8
D/OkHttp: Content-Length: 149456
D/OkHttp: ? ?? ???JFIF?? ??H? ? H? ???? ???C??
D/OkHttp: "##! %*5-%'2( .?/279<<<$-BFA:F5;<9?? ? ? C
D/OkHttp: 9& &99999999999999999999999999999999999999999999999999??? ? ? 8"?? ? ? ?? ?? ??? ? ????? ??? ? ??? ???? ?? ??? ? ? ?? ?? ? ? ? ?? ?? ????? ? ??? ???? ????????? |?? ? /n?s??y?]8ug?7?R? ?? ???h?tΘa?T? T<?U? ? ?z? ? ?+3C? w??tdf??=<???? ??fN??s??x??hhzd??X~? X?? i?{~/? <^??~=zX??\??4?U?ɡ)I? ? ? ? ??? ? ??? ???? ? ? ? ?$??@? ?? iM?"J? R 2? f?MK5x#w?????r?I?3?Y? ?l?? ? V?Bj??>{? ? t?u??? ? ]? ? ?? g>?o? ?o?? ? dM?U? ?? ??? J?R??<? +?;? ??? ? ? ???? OG>? ? ?? =?5?L?9?&???_/\?yu?? ~|*,??? My? r????? ? ? ?='?d?=?t*? ?*? Y? ? (???? ? ? ? ?? ? ? ? ? ? ?? YB i? Jlv??d? "l? ???Y? ? 4??X? 7? ?? ;?? sY? \κ+?N? ?;? L? ?&?(? MJ? ?? @w~~?? ? a?qs? ?m7??y? ? ?Ns? \?C? g??>? ??N%??N? ?gs?Q??c??? ?Z?t? ? ?x?? {?? ^_}s? s?? gO? ? ??? N?|}?;? ?y?y? ǎ|?v?? N? l?????? ?????*k5?(??????? ? ? 1$?B? ?j?+,?l? ?? hN?? U? <sgb?g?x? S??;;c?,? ?7?0Z?J?I? r??X?9? t? '\? 1W+
D/OkHttp: [?? ????=/X? ? ?n??T*4? u? ?<? ??? ?s? q?? ?? ??c???\?6? YV?p??? ?oB%??|? s?? ?? ? ? ?? ??{?? g??k?}?t??d{]^W???v?WB? x???|z9? >V?{ǒ>?o?? Y? ???xk? k7? ?? {w????b?!JQjRQ%RH?%8? H??Q? ?Ys? {??? u??(?`?b\?? k? cC:u#???d?C?? &? ?W.CXd?e?? N? ?n? ? ? ?.?%v?,.zW?>??&??+??r??S'? .n? [ V? ?q??oGL? ,:?S?? ? ???/?o<???,?B???;??? ?? ? ^[?#Lm?? 7.Q? 6sONz??fwN?
D/OkHttp: ?? ?,? \????
D/OkHttp: ? ??U<??? 1?Z?? ?=?? pn?~q?? [-?P?? =? j?va? R? ?? 4X*??? nv?H? ?j?j?p? ? `h#-???qiA?U????? x? &v?b? R?? o?.??H[M5??Y??5?>%Y?j???? x? 2.m??=??GG???
D/OkHttp: \? D? ?(?JK9<J? ? ?JE?jl??pW
D/OkHttp: ??}? ?i?6??R? ?:!J??FT?!e???
D/OkHttp: ??? ?:??5?? ??%? ? `? |? ??;z?G? ?[?P? ??N=???T??X? -?okNe?? ?Y??f8?`:?P? ??x? 1?I?g ?0? )? fe*P?qU? ~?jSY%?? gɡR?(?$A? |y?}??s?2?<? /? ? 4? s??@-?,?? AZ?az?,?? bl?.?? WD? ??? ?? q? X?u}?+G? z?h8=?w[`?j??g&q?c? ???????<|??|? 1???? q^? ? ?
D/OkHttp: 5? ?)x???:*dK? ?|?KPz5v?4?+?>eO?4??i?P2F?&\9? ?? ? -V?esf~&F?Q?? S?\??? 8{? ? *B?1qVO?? ??-S?? !????? ? ? ? ?*6??
D/OkHttp: 3? 5W?r? x??+? \? r? ? ? 6? ?C? ?Ms,H?AE??=q?? ????(??f?=,?? ? ?Z??+????L??<??v_i-? m|? ?? ?6??L? ??=?4? Y?{? W? ?9=?? \AW?? ? ~?? {@!?^ Z6??,?k>|? ?C
D/OkHttp: aZ? ? -?ы? ?R?K? ? ?1?6`'?? F%/4wZ?Cn? ??? [?]?el?? U&[?? ?1db-4???? ?? ??~er!?4??>ji? ]??AV?[v??e??`θo??? 帏!(??Pk?XCI?? Glk-p??p ? B?b???ae??? d? ]-|"? ?*? ?`??l?? Tmn`? ??
D/OkHttp: R? G??h? DETp???i? ??^? ? ? ?u?E??1?wW%?<?????? ??3e? ?V?? ?? **m??9V??O?R??f? b? D/OkHttp: ? ?j%)^? $?? g?\?Qm^`? ? D/OkHttp: ? ?[*?\?@/T@,?|@\$F? ????v_??uA?? ? :?9>%B? ??? 1 =?D]{? "? ? *^?? q1? ? i?? B?bs?L_?? ? ? e? ?W?2??pDR?Q??M?? ?{?? ? ?7S? ?? ?? Dzcb\? ??? ??0??? ? ? u? h?? ?e?? 7X? ? )? s{??DIqf???QdM? ?V?? ? ? ?r?? MTk?=?? +? >b0?b?? ?i?\? lI??H?P? ? ,?Pn[]??.? `.X? =A?I?P? @?<~??Px??.??? 9?(? ?:=? ? 5E?n? !l??? 5???ee_??'[???? p? d??1? )g?s<??? ?kop?вd? 19m?ft??ab??? ? ???? j?5/pT?M?xBb??8???z?? ? ??? wX??V??|~x???????? c?Rsx? ?? D???ixH??ud?50??MΘ7? ??<? ^I???i?`?????f?A? ?? ?? ? ?? ? ;?U? H? ?? ?a~?W臸?@O?'u\-???? ?? ? CN,? ? ??-? ??@?+"n? :y???G |S??C?F5?? ? ??Ix??? ??)?????b 22???jRj??? ?j?,K?K"¥</?G?w/ *? W? ? ? ?sn??L?? ??n? n? ???? k??? ? "? *? ?~?9? ?<4?,c?d>?EG??iB? ?0+??i? Y??D?? ?p?? ???? ? S|.?2???# &?? "v?Y?? P?? O?#EK? ? ? ,J? 6U? >a???;?-rM??@? ?? ^b??@??K? ???? PI??4? qM|? ?V? ? h[Ld? ?R????or? U?M??)_?J?^S? 41n}?@n|??
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="cause"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: text/plain;charset=UTF-8
D/OkHttp: Content-Length: 33
D/OkHttp: 对货物数量、质量有异议
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="details"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: text/plain;charset=UTF-8
D/OkHttp: Content-Length: 9
D/OkHttp: 哈哈哈
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="status"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: text/plain;charset=UTF-8
D/OkHttp: Content-Length: 1
D/OkHttp: 4
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="pickupId"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: text/plain;charset=UTF-8
D/OkHttp: Content-Length: 6
D/OkHttp: 105329
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="connectphone"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: text/plain;charset=UTF-8
D/OkHttp: Content-Length: 11
D/OkHttp: 13xxxxxxxxx
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108
D/OkHttp: Content-Disposition: form-data; name="connectname"
D/OkHttp: Content-Transfer-Encoding: binary
D/OkHttp: Content-Type: text/plain;charset=UTF-8
D/OkHttp: Content-Length: 3
D/OkHttp: 111
D/OkHttp: --f3e7369a-ead9-46e2-9ddd-448442fd5108--
D/OkHttp: --> END POST (300580-byte body)

六、代码托管

https://github.com/honghailiang/RetrofitUpLoadImage

七、效果图:

八、服务端代码

FileItemFactory factory = new DiskFileItemFactory();
ServletFileUpload upload = new ServletFileUpload(factory);
File directory = null;
List<FileItem> items = new ArrayList<FileItem>(); InputStream is = null; FileOutputStream fos = null; try {
items = upload.parseRequest(request);
// 得到全部的文件
Iterator<FileItem> it = items.iterator();
while (it.hasNext()) {
FileItem fItem = (FileItem) it.next();
String fName = "";
Object fValue = null;
if (fItem.isFormField()) { // 普通文本框的值
fName = fItem.getFieldName();
fValue = fItem.getString("UTF-8"); if("pickupId".equals(fName)){
pickupAppeal.setPickupId(fValue.toString());
}else if("cause".equals(fName)){
pickupAppeal.setCause(fValue.toString());
}else if("connectname".equals(fName)){
pickupAppeal.setConnectname(fValue.toString());
}else if("connectphone".equals(fName)){
pickupAppeal.setConnectphone(fValue.toString());
}else if("details".equals(fName)){
pickupAppeal.setDetails(fValue.toString());
}else if("status".equals(fName)){
String status = fValue.toString();
BigDecimal big = new BigDecimal(status);
pickupAppeal.setStatus(big);
} //map.put(fName, fValue);
} else { // 获取上传文件的值
fName = fItem.getFieldName();
fValue = fItem.getInputStream();
String name = fItem.getName();
if (name != null && !("".equals(name))) {
name = name.substring(name.lastIndexOf(File.separator) + 1);
int lenN =name.indexOf(".");
String suf = name.substring(lenN, name.length()); String day = DateUtil.format(Calendar.getInstance().getTime(),
"yyyy-MM-dd");
String path = PATH+File.separator+day;
directory = new File(path);
if (!directory.exists()) {
directory.mkdirs();
} String preFile =UUID.randomUUID().toString().replace("-", ""); String filePath = path + File.separator+preFile+suf;
String serverPath = day+ File.separator+preFile+suf;
map.put(fName, serverPath);
map.put(fName+"m", name);
is = fItem.getInputStream();
fos = new FileOutputStream(filePath);
byte[] buffer = new byte[1024];
int len = 0;
while ((len = is.read(buffer, 0, 1024)) != -1) {
fos.write(buffer, 0, len);
}
fos.flush(); }
}
}
} catch (Exception e) {
pLog.error("接收參数错误:" + e.getMessage());
resultInfo.setStatus(ComStatus.RESULTINFO_STATUS_FAILE);
resultInfo.setMessage(ComStatus.RESULTINFO_MESSAGE_FAILE); resultInfo.setData(map);
resReslt.setResData(resultInfo);
} finally {
try {
if (null != fos) {
fos.close();
} if (null != is) {
is.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}




【Android实战】----基于Retrofit实现多图片/文件、图文上传的更多相关文章

  1. HTML5实现图片文件异步上传

    原文:HTML5实现图片文件异步上传 利用HTML5的新特点做文件异步上传非常简单方便,本文主要展示JS部分,html结构.下面的代码并未使用第三发库,如果有参照,请注意一些未展现出来的代码片段.我这 ...

  2. ssh整合问题总结--在添加商品模块实现图片(文件)的上传

    今天在做毕设(基于SSH的网上商城项目)中碰到了一个文件上传的需求,就是在后台管理员的商品模块中,有一个添加商品,需要将磁盘上的图片上传到tomcat保存图片的指定目录中: 完成这个功能需要两个步,第 ...

  3. div中粘贴图片并上传服务器 div中拖拽图片文件并上传服务器

    应用简介:此文主要是描述如何在前端div中直接ctrl+v 粘贴图片,并上传到服务器,包括拖拽图片文件到div中 应用场景描述:用QQ或者其它切图软件截图,在指定的div中ctrl+v 粘贴并显示,点 ...

  4. 从0开始做一个的Vue图片/ 文件选择(上传)组件[基础向]

    原文:http://blog.csdn.net/sinat_17775997/article/details/58585142 之前用Vue做了一个基础的组件 vue-img-inputer ,下面就 ...

  5. vue-quill-editor 封装成组件;图片文件流上传;同一页面多个编辑器样式异常解决办法

    使用方法: 引入并注册组件,然后直接使用: @getcode是同步获取编辑器内容的::contentDefault是编辑器的默认内容: 注意:如果同一个页面多个编辑器,参数id不能相同,否则只有第一个 ...

  6. Spring Boot 2.x基础教程:多个文件的上传

    昨天,我们介绍了如何在Spring Boot中实现文件的上传.有读者问:那么如果有多个文件要同时上传呢?这就马上奉上,当碰到多个文件要同时上传的处理方法. 动手试试 本文的动手环节将基于Spring ...

  7. 基于h5的图片无刷新上传(uploadifive)

    基于h5的图片无刷新上传(uploadifive) uploadifive简介 了解uploadify之前,首先了解来一下什么是uploadify,uploadfy官网,uploadify和uploa ...

  8. android下大文件分割上传

    由于android自身的原因,对大文件(如影视频文件)的操作很容易造成OOM,即:Dalvik堆内存溢出,利用文件分割将大文件分割为小文件可以解决问题. 文件分割后分多次请求服务. //文件分割上传 ...

  9. Android 发送HTTP GET POST 请求以及通过 MultipartEntityBuilder 上传文件(二)

    Android 发送HTTP GET POST 请求以及通过 MultipartEntityBuilder 上传文件第二版 上次粗略的写了相同功能的代码,这次整理修复了之前的一些BUG,结构也大量修改 ...

随机推荐

  1. openstack vm实例pxe无法启动

    问题如下: 创建vm没有任何报错,打开控制台提示: SeaBIOS (versio xxxxxxx) Machine UUID xxxxxxxxxx iPXE (http://ipxe.org) 00 ...

  2. jni java C/C++ 相互调用

    韩梦飞沙  韩亚飞  313134555@qq.com  yue31313  han_meng_fei_sha java 中  声明 一个 native 方法 用javah命令 生成 包含 nativ ...

  3. Python入门,以及简单爬取网页文本内容

    最近痴迷于Python的逻辑控制,还有爬虫的一方面,原本的目标是拷贝老师上课时U盘的数据.后来发现基础知识掌握的并不是很牢固.便去借了一本Python基础和两本爬虫框架的书.便开始了自己的入坑之旅 言 ...

  4. php -- 解决php连接sqlserver2005中文乱码问题(附详细解决方法)

    @_@~~ --php5.2 --phpstudy --apache --sqlserver2005 @_@~~问题描述 问题一:php连接sqlsever2005,输入中文,然后查询sqlserve ...

  5. PHP -- 简单表单提交

    网上看博文,一步步入门~~ 简单表单,简单提交 @_@!! <?php //php代码部分开始 echo "<html>"; echo "<hea ...

  6. VK Cup 2016 - Qualification Round 2 A. Home Numbers 水题

    A. Home Numbers 题目连接: http://www.codeforces.com/contest/638/problem/A Description The main street of ...

  7. Markdown 简明语法手册 - 作业

    目录 Cmd Markdown 简明语法手册 1. 内容目录 2. 标签分类 3. 删除线 水平线--- 1. 斜体和粗体 2. 分级标题 标题1 标题2 标题3 3. 外链接 4. 无序列表 5. ...

  8. 关于Oracle安装完毕后,登录时遇到的错误的解决的方法

    1 提示无监听服务 解决方法:打开Net Configuration Assistant 依照提示删除现有的监听服务,然后又一次建立一个就可以. 2 SQL Plus登陆时提示username或pas ...

  9. STN1110 Multiprotocol OBD to UART Interpreter

    http://www.obdsol.com/stn1110/ Safe, secure bootloader. Reflash the firmware in the field, even over ...

  10. Changing the Output Voltage of a Switching Regulator on the Fly

    http://www.powerguru.org/changing-the-output-voltage-of-a-switching-regulator-on-the-fly/ There are ...