我正在寻找另一种从android.net.Uri获取查询参数名称的方法。 getQueryParameterNames()需要api级别11.我想对任何低级api做同样的事情。 我在看getQuery(),它会返回'?'之后的所有内容。标志。最好的解决方法是解析该字符串并在'='之前搜索所有内容并捕获它吗?我根本不知道每次都会显示什么查询参数。
答案 0 :(得分:12)
API的唯一问题<图11的实施例是没有实现该方法。我想最好的想法是查看Android源代码并使用API> = 11的实现。即使在较旧的API上,这也应该让您获得绝对的功能。
这个来自4.1.1,修改后将Uri作为参数,所以你可以马上使用它:
/**
* Returns a set of the unique names of all query parameters. Iterating
* over the set will return the names in order of their first occurrence.
*
* @throws UnsupportedOperationException if this isn't a hierarchical URI
*
* @return a set of decoded names
*/
private Set<String> getQueryParameterNames(Uri uri) {
if (uri.isOpaque()) {
throw new UnsupportedOperationException("This isn't a hierarchical URI.");
}
String query = uri.getEncodedQuery();
if (query == null) {
return Collections.emptySet();
}
Set<String> names = new LinkedHashSet<String>();
int start = 0;
do {
int next = query.indexOf('&', start);
int end = (next == -1) ? query.length() : next;
int separator = query.indexOf('=', start);
if (separator > end || separator == -1) {
separator = end;
}
String name = query.substring(start, separator);
names.add(Uri.decode(name));
// Move start to end of name.
start = end + 1;
} while (start < query.length());
return Collections.unmodifiableSet(names);
}
如果你想自己深入研究,这是原始代码:
答案 1 :(得分:3)
如果您有java.net.URI
(或创建一个),则可以使用URLEncodedUtils.parse
将参数和值设为NameValuePair
:
Map<String, String> parameters = Maps.newHashMap();
List<NameValuePair> params = URLEncodedUtils.parse(uri, "UTF-8");
for (NameValuePair param : params) {
parameters.put(param.getName(), param.getValue());
}
答案 2 :(得分:2)
我同意福克斯的观点,最好的选择是从最新的Android版本中获取代码并添加到您的代码库中。每次我遇到这样的问题时,我都会创建一个抽象版本特性的方法。它是这样的:
public class FWCompat {
public static boolean isFroyo_8_OrNewer() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.FROYO;
}
public static boolean isGingerbread_9_OrNewer() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.GINGERBREAD;
}
public static boolean isHoneycomb_11_OrNewer() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB;
}
public static boolean isHoneycomb_13_OrNewer() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB_MR2;
}
public static boolean isJellyBean_16_OrNewer() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN;
}
}
@SuppressLint("NewApi")
public class FWUriCompat {
public static Set<String> getQueryParameterNames(Uri uri) {
if (FWCompat.isHoneycomb_11_OrNewer()) {
return uri.getQueryParameterNames();
}
return FW_getQueryParameterNames(uri);
}
private static Set<String> FW_getQueryParameterNames(Uri uri) {
if (uri == null) {
throw new InvalidParameterException("Can't get parameter from a null Uri");
}
if (uri.isOpaque()) {
throw new UnsupportedOperationException("This isn't a hierarchical URI.");
}
String query = uri.getEncodedQuery();
if (query == null) {
return Collections.emptySet();
}
Set<String> names = new LinkedHashSet<String>();
int start = 0;
do {
int next = query.indexOf('&', start);
int end = (next == -1) ? query.length() : next;
int separator = query.indexOf('=', start);
if (separator > end || separator == -1) {
separator = end;
}
String name = query.substring(start, separator);
names.add(Uri.decode(name));
// Move start to end of name.
start = end + 1;
} while (start < query.length());
return Collections.unmodifiableSet(names);
}
}
答案 3 :(得分:1)
好的,这就是我想出来的。没有编译或测试它,所以没有保证
ArrayList<String> getQueryParamNames(String input)
{
ArrayList<String> result = new ArrayList<String>();
//If its everything after the ? then up to the first = is the first parameter
int start = 0;
int end = input.indexOf("=");
if (end == -1) return null; //No parameters in string
while (end != -1)
{
result.Add(input.substring(start, end)); //May need to do end - 1 to remove the =
//Look for next parameter, again may need to add 1 to this result to get rid of the &
start = input.indexOf("&", end);
if (start == -1) //No more parameters
break;
//If you want to grab the values you can do so here by doing
//input.substring(end, start);
end = input.indexOf("=", start);
}
return result;
}
我是在深夜编写的,没有对其进行测试,因此您可能需要通过添加或减去1来调整一些调用。此外,我可能忘记了添加到List
的确切语法。我想评论其他人看到的任何错误,但这是它的一般要点。我有一种感觉,我在某个地方忘记了;
。
编辑:将结果设置为新的ArrayList而不是LinkList,如下所示