Kotlin入门:Android开发新语言快速上手
去年双11期间,我正在家里远程摸鱼(划掉)——认真写爬虫脚本抓某宝销量数据,结果外包老板一个钉钉电话打过来:“老张,客户那边急着要个安卓App原型,下周一就要演示,你不是会Java吗?顺便用Kotlin重写一下吧,人家说现在流行这个。”
我当时差点把咖啡喷到机械键盘上。我确实写了四年外包代码,但主要在搞云原生那一套,K8s YAML比XML写得还熟。至于Android?上次碰还是大学课程设计,用Eclipse+ADT搭了个“计算器”,界面丑得连我妈都嫌弃。
但没办法,外包人的宿命就是“啥都能接”。为了保住饭碗,我硬着头皮翻出尘封的《第一行代码》,一边开ChatGPT查语法,一边在AS里狂点Run,结果首屏就Crash——Unresolved reference: findViewById。那一刻,我真的想砸电脑。
为啥非得学Kotlin?
说实话,一开始我是抗拒的。Java不香吗?至少不会动不动就报lateinit property has not been initialized这种玄学错误。但架不住现实毒打:
- 客户需求:客户明确要求用Kotlin,说“显得技术栈新”;
- 团队趋势:我们外包公司虽然项目杂,但新项目基本默认Kotlin了;
- 个人发展:想跳槽去大厂,JD清一色写着“熟悉Kotlin者优先”。
再加上,我发现用Kotlin写爬虫脚本(比如用Ktor + Jsoup)比Java简洁太多,一行data class直接搞定JSON映射,再也不用手动写getter/setter。这让我对Kotlin的好感度直线上升。
入门踩坑实录:从“Hello World”到上线崩溃
1. 环境配置:别被Gradle版本坑了
刚新建项目,Sync就失败。报错如下:
Could not find org.jetbrains.kotlin:kotlin-gradle-plugin:1.9.0.
查了半天才发现,Android Studio自带的Kotlin插件版本和项目里build.gradle写的不一致。建议直接用AS最新稳定版(我用的是Flamingo),新建项目时勾选“Include Kotlin support”,省得手动配。
💡 最佳实践:永远用AS向导创建Kotlin项目,别手贱改
buildscript里的版本号,除非你想体验“依赖地狱”。
2. 空安全:从崩溃到优雅
第一次写RecyclerView adapter,自信满满地写:
var items: List<String>? = null
然后在getItemCount()里直接返回items.size。结果一运行——Boom!NullPointerException。
Kotlin的空安全机制其实很友好,只要你愿意用?.、?:、!!这些操作符。后来我改成:
override fun getItemCount() = items?.size ?: 0
或者更激进一点,直接声明为非空:
var items: List<String> = emptyList()
从此告别NPE(至少在Kotlin代码里)。
3. 扩展函数:让代码“会说话”
有次产品经理要求给TextView加个“自动截断并显示省略号”的功能。Java时代可能要写个Util类,但现在:
fun TextView.ellipsize(maxLength: Int) {
if (text.length > maxLength) {
text = text.substring(0, maxLength) + "..."
}
}
然后在Activity里直接调:
myTextView.ellipsize(20)
读起来像英语句子一样自然。这种“DSL感”是Kotlin最让我上头的地方。
实战:从零写个天气App(外包版)
为了练手,我用周末两天撸了个极简天气App,核心功能就三个:定位、请求API、展示数据。全程Kotlin + Coroutines + Retrofit。
关键代码片段
Retrofit接口定义(配合data class简直爽飞):
data class WeatherResponse(
val city: String,
val temperature: Float,
val description: String
)
interface WeatherApi {
@GET("weather")
suspend fun getWeather(@Query("lat") lat: Double, @Query("lon") lon: Double): WeatherResponse
}
协程处理网络请求(告别Callback地狱):
lifecycleScope.launch {
try {
val weather = api.getWeather(lat, lon)
binding.textView.text = "${weather.city}: ${weather.temperature}°C"
} catch (e: Exception) {
// 友好提示,别让用户看到Toast堆成山
showError("网络开小差了,请重试~")
}
}
📌 注意:别在
onCreate里直接launch协程!一定要绑定生命周期,否则内存泄漏等着你。
性能与兼容性:别只顾着炫技
Kotlin虽然爽,但也有坑:
- 方法数膨胀:每个lambda都会生成匿名内部类,APK体积悄悄变大。建议开启ProGuard/R8混淆。
- 低版本兼容:有些高阶语法(比如
repeat函数)在API 21以下可能有问题。测试机一定要覆盖Android 8.0及以下。 - 启动速度:冷启动比纯Java慢约100-200ms(实测数据)。优化方案:减少init块、懒加载。
我整理了一个简单对比表:
| 维度 | Java | Kotlin(推荐写法) |
|---|---|---|
| 空安全 | 全靠自觉 | 编译期强制检查 |
| 代码量 | 冗长 | 减少30%-50% |
| 构建速度 | 稍快 | 稍慢(但增量编译后差距缩小) |
| 团队上手成本 | 老程序员友好 | 新人需适应空安全/扩展函数 |
发布上架:别倒在最后一公里
写完App,打包上传到华为应用市场,结果被拒——理由是“使用了非官方定位SDK”。原来我图省事用了高德,但客户要求只能用系统LocationManager。
赶紧重构,用Kotlin协程封装系统定位:
suspend fun getCurrentLocation(context: Context): Location? = withContext(Dispatchers.IO) {
val lm = context.getSystemService(Context.LOCATION_SERVICE) as LocationManager
// ... 请求权限、获取最后已知位置
}
虽然代码多了点,但过审了。教训:外包项目一定要问清合规要求,别等上线前夜才改。
学习资源推荐
- 书籍:《Kotlin实战》(Dmitry Jemerov著)——比《第一行代码》更深入,适合有Java基础的人。
- 技术分享:关注Kotlin中文社区公众号,每周都有源码解析;B站搜“Kotlin Coroutines”,有位UP主讲得特别接地气。
- AI辅助:我重度依赖Claude。比如问它:“如何用Kotlin写一个线程安全的单例?” 它直接给我
object声明 + 解释,比Stack Overflow快多了。
最后几句真心话
作为外包老兵,我见过太多团队为了“技术潮流”盲目切Kotlin,结果新人看不懂apply、also、let的区别,维护成本反而上升。所以我的建议是:
- 小项目/新项目:大胆上Kotlin,配合ViewBinding + Coroutines,开发效率飞起;
- 老项目迁移:别一次性重写!用“渐进式替换”——新功能用Kotlin,旧Java代码逐步改造;
- 团队培训:花半天时间集体过一遍空安全和扩展函数,比后期debug省十倍时间。
现在回头看,那个双11的紧急需求,反而逼我入了Kotlin的坑。上周五晚上,我把天气App优化完,点了“Generate Signed Bundle”,看着Google Play Console里绿色的“Release successful”,心里居然有点小骄傲。
毕竟,一个靠爬虫和K8s吃饭的外包仔,居然也能写出用户量破千的App(虽然是内部工具)。技术这东西,有时候真得被“逼”一把。
共勉。

评论 0