跳到主要内容

移动App开发入门

原生开发与跨平台方案

移动开发技术栈

原生开发
├── iOS:Swift / Objective-C
└── Android:Kotlin / Java

跨平台方案
├── React Native (JavaScript)
├── Flutter (Dart)
├── uni-app (Vue)
└── Taro (React)

混合开发
├── Cordova
├── Ionic
└── Capacitor

跨平台首选:Flutter

环境准备

# 下载Flutter SDK
# https://flutter.dev/docs/get-started/install

# 验证安装
flutter doctor

# 创建项目
flutter create my_app
cd my_app
flutter run

Flutter基础

import 'package:flutter/material.dart';

void main() {
runApp(MyApp());
}

class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: '我的App',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: HomePage(),
);
}
}

class HomePage extends StatefulWidget {
@override
_HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
int _counter = 0;

void _increment() {
setState(() {
_counter++;
});
}

@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('首页'),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
'点击次数:',
style: TextStyle(fontSize: 18),
),
Text(
'$_counter',
style: TextStyle(fontSize: 48, fontWeight: FontWeight.bold),
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _increment,
child: Icon(Icons.add),
),
);
}
}

Flutter常用组件

// 列表
ListView.builder(
itemCount: items.length,
itemBuilder: (context, index) {
return ListTile(
leading: Icon(Icons.star),
title: Text(items[index].title),
subtitle: Text(items[index].description),
onTap: () => _handleTap(items[index]),
);
},
)

// 网格
GridView.count(
crossAxisCount: 2,
children: items.map((item) => Card(
child: Center(child: Text(item.name)),
)).toList(),
)

// 表单
TextFormField(
decoration: InputDecoration(
labelText: '用户名',
hintText: '请输入用户名',
prefixIcon: Icon(Icons.person),
),
validator: (value) {
if (value == null || value.isEmpty) {
return '用户名不能为空';
}
return null;
},
)

// 按钮
ElevatedButton(
onPressed: _submit,
child: Text('提交'),
)

React Native入门

import React, { useState } from 'react';
import {
View,
Text,
Button,
FlatList,
StyleSheet,
TouchableOpacity
} from 'react-native';

const App = () => {
const [count, setCount] = useState(0);
const [items, setItems] = useState([
{ id: '1', title: '项目1' },
{ id: '2', title: '项目2' },
]);

return (
<View style={styles.container}>
<Text style={styles.title}>计数器: {count}</Text>
<Button title="增加" onPress={() => setCount(count + 1)} />

<FlatList
data={items}
keyExtractor={item => item.id}
renderItem={({ item }) => (
<TouchableOpacity style={styles.item}>
<Text>{item.title}</Text>
</TouchableOpacity>
)}
/>
</View>
);
};

const styles = StyleSheet.create({
container: {
flex: 1,
padding: 20,
backgroundColor: '#fff',
},
title: {
fontSize: 24,
fontWeight: 'bold',
marginBottom: 20,
},
item: {
padding: 15,
borderBottomWidth: 1,
borderBottomColor: '#eee',
},
});

export default App;

原生开发:Swift (iOS)

import SwiftUI

struct ContentView: View {
@State private var count = 0

var body: some View {
VStack(spacing: 20) {
Text("计数器")
.font(.title)

Text("\(count)")
.font(.system(size: 60, weight: .bold))

HStack(spacing: 20) {
Button("-") { count -= 1 }
.buttonStyle(.bordered)

Button("+") { count += 1 }
.buttonStyle(.borderedProminent)
}
}
.padding()
}
}

// 列表视图
struct ListView: View {
let items = ["苹果", "香蕉", "橙子"]

var body: some View {
NavigationView {
List(items, id: \.self) { item in
Text(item)
}
.navigationTitle("水果列表")
}
}
}

原生开发:Kotlin (Android)

// MainActivity.kt
class MainActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
MyAppTheme {
CounterScreen()
}
}
}
}

@Composable
fun CounterScreen() {
var count by remember { mutableStateOf(0) }

Column(
modifier = Modifier.fillMaxSize(),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.Center
) {
Text(
text = "计数器",
style = MaterialTheme.typography.headlineLarge
)

Text(
text = "$count",
style = MaterialTheme.typography.displayLarge
)

Row(horizontalArrangement = Arrangement.spacedBy(16.dp)) {
Button(onClick = { count-- }) {
Text("-")
}
Button(onClick = { count++ }) {
Text("+")
}
}
}
}

技术选型建议

方案优势适用场景
Flutter性能好、UI一致对性能有要求的App
React Native生态丰富、热更新已有React经验团队
原生开发最佳性能、完整API大厂核心App
uni-app一套代码多端小程序+App

学习路线图

第1阶段:入门 (1-2个月)
├── 选择一个框架
├── 基础组件使用
├── 布局与样式
└── 状态管理

第2阶段:进阶 (2-3个月)
├── 路由导航
├── 网络请求
├── 本地存储
└── 第三方库集成

第3阶段:实战 (2-3个月)
├── 完整App开发
├── 发布上架流程
├── 性能优化
└── 错误监控

本章小结

  • 跨平台:Flutter/RN一套代码多端运行
  • 原生:Swift/Kotlin最佳性能
  • 选型:根据团队和项目需求选择
  • 学习:先掌握一个框架再扩展

→ 继续阅读:38-数据分析与数据科学