面试题答案
一键面试使用Future和async/await异步加载网络数据的基本步骤
- 导入网络请求库:
在Flutter项目中,常用的网络请求库是
http
库。在pubspec.yaml
文件中添加依赖:
dependencies:
http: ^0.13.4
然后在代码文件头部导入:
import 'package:http/http.dart' as http;
- 创建异步函数:
使用
async
关键字定义一个异步函数,该函数返回一个Future
对象。例如:
Future<String> fetchData() async {
final response = await http.get(Uri.parse('https://example.com/api/data'));
if (response.statusCode == 200) {
return response.body;
} else {
throw Exception('Failed to load data');
}
}
在上述函数中,await
关键字等待http.get
操作完成,该操作返回一个Future<Response>
对象。如果请求成功(状态码为200),则返回响应体;否则抛出异常。
3. 调用异步函数:
在需要加载数据的地方调用这个异步函数。例如,在initState
方法中:
class MyWidget extends StatefulWidget {
@override
_MyWidgetState createState() => _MyWidgetState();
}
class _MyWidgetState extends State<MyWidget> {
String data = '';
@override
void initState() {
super.initState();
fetchData().then((value) {
setState(() {
data = value;
});
}).catchError((error) {
print('Error: $error');
});
}
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: Text(data),
),
);
}
}
也可以使用async/await
语法糖来处理:
class _MyWidgetState extends State<MyWidget> {
String data = '';
@override
void initState() {
super.initState();
loadData();
}
Future<void> loadData() async {
try {
String result = await fetchData();
setState(() {
data = result;
});
} catch (error) {
print('Error: $error');
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: Text(data),
),
);
}
}
处理加载过程中的错误
- 使用try - catch块:
在调用异步函数的地方,使用
try - catch
块捕获可能抛出的异常。如上述loadData
函数中的示例:
Future<void> loadData() async {
try {
String result = await fetchData();
setState(() {
data = result;
});
} catch (error) {
print('Error: $error');
}
}
- 使用catchError方法:
也可以在
Future
对象上调用catchError
方法来捕获错误。例如:
fetchData().then((value) {
setState(() {
data = value;
});
}).catchError((error) {
print('Error: $error');
});
通过缓存机制提升性能
- 内存缓存: 可以在应用程序内存中缓存数据。例如,使用一个静态变量来存储数据:
class DataFetcher {
static String? cachedData;
static Future<String> fetchData() async {
if (cachedData != null) {
return cachedData!;
}
final response = await http.get(Uri.parse('https://example.com/api/data'));
if (response.statusCode == 200) {
cachedData = response.body;
return cachedData!;
} else {
throw Exception('Failed to load data');
}
}
}
- 本地存储缓存:
使用
shared_preferences
库将数据缓存到本地存储。首先在pubspec.yaml
中添加依赖:
dependencies:
shared_preferences: ^2.0.15
然后在代码中使用:
import 'package:shared_preferences/shared_preferences.dart';
Future<String> fetchData() async {
final prefs = await SharedPreferences.getInstance();
String? cachedData = prefs.getString('cachedData');
if (cachedData != null) {
return cachedData;
}
final response = await http.get(Uri.parse('https://example.com/api/data'));
if (response.statusCode == 200) {
prefs.setString('cachedData', response.body);
return response.body;
} else {
throw Exception('Failed to load data');
}
}
这样,下次请求相同数据时,先从缓存中读取,若缓存中没有则再发起网络请求,并将新数据缓存起来。