在Java中没有初始化和用法的字段声明
问题描述:
我有一个问题涉及到java编译器的行为以及android的不同API。在Java中没有初始化和用法的字段声明
我有代表蓝牙LE连接的类。我在这个类中检查API的版本,以了解哪些方法可以扫描我必须使用的设备。那就是:
public class BleConnector{
private MyScanCallback _scanCallback;
private LeScanHandle _leScanHndl;
private BluetoothAdapter _bluetoothAdapter;
/**
* Initializes new instance of BLE connector
*/
public BleConnector()
{
//Creating handle for device scan callback;
_leScanHndl = new LeScanHandle();
//Check version of android api
//If it is bigger of equal to 21
//create scan callback for higher versions
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
{
_scanCallback = new ScanCallback(_leScanHndl);
}
}
public void startScan(Context context) throws PermissoinException
{
final BluetoothManager bluetoothManager = (BluetoothManager) context.getSystemService(Context.BLUETOOTH_SERVICE);
_bluetoothAdapter = bluetoothManager.getAdapter();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
{
if (ContextCompat.checkSelfPermission(context, Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED)
{
_bluetoothAdapter.getBluetoothLeScanner().startScan(_scanCallback);
}
else
{
throw new PermissoinException("Location permission does not allowed");
}
}
else
{
_bluetoothAdapter.startLeScan(_leScanHndl);
}
//TODO notify
}
public void stopScan()
{
if (_bluetoothAdapter != null)
{
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
{
_bluetoothAdapter.getBluetoothLeScanner().stopScan(_scanCallback);
} else
{
_bluetoothAdapter.stopLeScan(_leScanHndl);
}
}
//TODO notify
}
private void connectToDevice(BluetoothDevice device)
{
//TODO notify
//TODO connect gatt
}
类MyScanCallback标有@TargetAPI 21,当然我并不想用它来工作,如果我的设备的版本低于21
正如你可以看到所有的用法并且初始化_scanCallback都在之内,如果是声明。所以我的问题是:
我将有一设备带有声明private MyScanCallback _scanCallback;
任何麻烦与API < 21或编译器,如果没有初始化和_scanCallback惯例将删除呢?
谢谢!
UDT
哦,我并没有说MyScanCallback继承ScanCallback至极从21 API级别public class MyScanCallback extends ScanCallback
答
@TargetApi 21只是防止任何编译错误所用的任何新的API。 Byt实际上避免了代码被执行,它必须被包裹在构建版本检查中,就像你在几个地方做过的一样。
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
{
}
所以在这种情况下,绝对是一个MyScanCallback的变量将被创建,但它不会在设备与API < 21实例化为您在构造函数中裹住版本检查。
正如您所提到的,它使用API 21中引入的ScanCallback,那么在旧版本中使用ScanCallback肯定会有问题。
为了摆脱这一点,我建议如下创建一个抽象类:
public abstract class BleConnector{
public abstract void startScan(Context context);
}
,然后创建两个类
public class BleConnectOldApi extends BleConnector{
public void startScan(Context context) throws PermissoinException {
//Your code here
}
}
和
@TargetApi(21)
public class BleConnect21Api extends BleConnector{
private MyScanCallback _scanCallback;
public void startScan(Context context) throws PermissoinException {
//Your code here
}
}
最后有工厂分类
public class BleConnectorFactory{
public static BleConnector getBleConnector() {
if (android.os.Build.VERSION.SDK_INT >= 21) {
return new BleConnect21Api();
}else{
return new BleConnectOldApi();
}
}
}
通过这种方式,您可以防止使用旧API版本中不存在的类的不需要的错误。
希望能帮助你。
噢,我没有说MyScanCallback继承了ScanCallback,它来自21 API级别的公共类EegScanCallback扩展了ScanCallback。那它不会有什么麻烦吗?这个类的领域的宣言 –
太棒了!感谢分享...更新我的答案相同。 –
非常感谢你的回答!好主意 –