Quantcast
Channel: CSDN博客移动开发推荐文章
Viewing all 5930 articles
Browse latest View live

iOS 网络编程 (四)JSON解析

$
0
0

1 JSON基础

JSON全称是JavaScript Object Notation,它是一种轻量级的数据交换格式。JSON数据格式既适合人进行读写,也适合计算机本身解析和生成。早期,JSON是JavaScript语言的数据交换格式,后来发展成为一种与语言无关的数据交换格式。JSON在许多编程语言中使用,包括java、C、Objcetive-C、C++、C#、JavaScript、Perl、Python等。JSON提供了多种语言之间的交换数据的能力,因此,JSON是一种非常理想的数据结构。

服务器返回给客户端的数据,一般都是JSON格式或者XML格式(文件下载除外)

资料网站:http://www.w3cschool.cc/

JSON主要有两种数据结构。

  1. key-value对组成的数据结构,类似于Objective-C中的字典NSDictionary,如:{"name" :"jack", "age" :10}
  2. 有序集合,类似于Objective-C中的NSArray,如:
    [
    { "firstName":"John" , "lastName":"Doe" },
    { "firstName":"Anna" , "lastName":"Smith" },
    { "firstName":"Peter" , "lastName":"Jones" }
    ]
JSON—OC对照表


JSON-OC转换

2 JSON解析方案

JSON的常见解析方案有4种:
苹果原生(自带):NSJSONSerialization性能最好
第三方框架:JSONKitSBJsonTouchJSON(性能从左到右,越差) 
提示:JSON本质上是一个特殊格式的字符串,注意不是NSStringJSON的解析是一个非常繁琐的工作!


解析

1 使用NSJSONSerialization解析

http://api.36wu.com/Weather/GetWeather这个网址获取天气信息需要申请key值,试用期小于1天。

-(void)JSONSerializationParse{
    NSURL *url = [NSURL URLWithString:@"http://api.36wu.com/Weather/GetWeather"];
    
    NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url];
    request.HTTPMethod = @"POST";
    //district表示区域id,authkey申请的试用值,只允许试用一天。所以过了2016/9/9就获取不到数据了,key自己去http://www.36wu.com申请试用。
    request.HTTPBody = [@"district=101010100&format=json&authkey=b0aa5ef944514793812734e0b36e5740" dataUsingEncoding:NSUTF8StringEncoding];
    [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * response, NSData * data, NSError * connectionError) {
        NSLog(@"conncetionError:%@",connectionError);
        NSLog(@"string:%@",[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
        NSDictionary *dictionary = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
        NSLog(@"dictionary:%@",dictionary);
        NSDictionary *dataDictionary = dictionary[@"data"];
        NSLog(@"weather=%@,refreshTime=%@",dataDictionary[@"weather"],dataDictionary[@"refreshTime"]);
    }];
}

打印如下:

2016-09-09 15:59:01.500 JSON解析[942:983924] conncetionError:(null)
2016-09-09 15:59:01.502 JSON解析[942:983924] string:{"data":{"areaid":101010100,"prov":"北京","city":"北京","district":"北京","dateTime":"2016年9月9日","temp":"31℃","minTemp":"18℃","maxTemp":"31℃","weather":"晴","windDirection":"西风","windForce":"2级","humidity":"27%","img_1":"1","img_2":"4","refreshTime":"15:54"},"message":"OK","status":200}
2016-09-09 15:59:01.503 JSON解析[942:983924] dictionary:{
    data =     {
        areaid = 101010100;
        city = "\U5317\U4eac";
        dateTime = "2016\U5e749\U67089\U65e5";
        district = "\U5317\U4eac";
        humidity = "27%";
        "img_1" = 1;
        "img_2" = 4;
        maxTemp = "31\U2103";
        minTemp = "18\U2103";
        prov = "\U5317\U4eac";
        refreshTime = "15:54";
        temp = "31\U2103";
        weather = "\U6674";
        windDirection = "\U897f\U98ce";
        windForce = "2\U7ea7";
    };
    message = OK;
    status = 200;
}
2016-09-09 15:59:01.508 JSON解析[942:983924] weather=晴,refreshTime=15:54

2 使用JSONKit解析

需要向工程中导入JSONKit.h和JSONKit.m文件。使用处需要引头文件

#import "JSONKit.h"

由于我导入的这个版本不支持ARC,所以需要对JSONKit.m文件设置禁止ARC


-(void)JSONKitParse{
    NSURL *url = [NSURL URLWithString:@"http://api.36wu.com/Train/GetTicketInquiry"];
    NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url];
    request.HTTPMethod = @"POST";
    //查询火车票接口
    request.HTTPBody = [@"startStation=北京&arriveStation=上海&date=2016-10-01&authkey=b0aa5ef944514793812734e0b36e5740" dataUsingEncoding:NSUTF8StringEncoding];
    [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * response, NSData * data, NSError * connectionError) {
        NSLog(@"conncetionError:%@",connectionError);
        NSLog(@"string:%@",[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
        //使用JSONkit方法
        NSDictionary *dictionary = [data objectFromJSONData];
        NSLog(@"dictionary:%@",dictionary);
        NSArray *dataAry = dictionary[@"data"];
        NSLog(@"dataAry count=%lu",(unsigned long)dataAry.count);
    }];
}

由于数据太多就不全贴出来了。

//只是打印的string中的一部分
{"train_no":"240000G1010C","train_code":"G101","start_station":"北京南","end_station":"上海虹桥","from_station":"北京南","to_station":"上海虹桥","start_time":"06:44","arrive_time":"12:38","day_difference":"0","lishi":"05:54","from_station_no":"01","to_station_no":"11","gg_num":"--","gr_num":"--","qt_num":"--","rw_num":"--","rz_num":"--","tz_num":"--","wz_num":"--","yb_num":"--","yw_num":"--","yz_num":"--","ze_num":"522","zy_num":"47","swz_num":"21"}
//这是dictionary中的一部分
{
            "arrive_time" = "12:38";
            "day_difference" = 0;
            "end_station" = "\U4e0a\U6d77\U8679\U6865";
            "from_station" = "\U5317\U4eac\U5357";
            "from_station_no" = 01;
            "gg_num" = "--";
            "gr_num" = "--";
            lishi = "05:54";
            "qt_num" = "--";
            "rw_num" = "--";
            "rz_num" = "--";
            "start_station" = "\U5317\U4eac\U5357";
            "start_time" = "06:44";
            "swz_num" = 21;
            "to_station" = "\U4e0a\U6d77\U8679\U6865";
            "to_station_no" = 11;
            "train_code" = G101;
            "train_no" = 240000G1010C;
            "tz_num" = "--";
            "wz_num" = "--";
            "yb_num" = "--";
            "yw_num" = "--";
            "yz_num" = "--";
            "ze_num" = 522;
            "zy_num" = 47;
        }

使用SBJson解析方法

需要导入SBJson.h文件

#import "SBJson.h"

-(void)SBJsonParse{
    NSURL *url = [NSURL URLWithString:@"http://api.36wu.com/Translate/GetTranslate"];
    NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url];
    request.HTTPMethod = @"POST";
    //翻译,不过服务下限了,翻译不出来。不过可以看一下SBJson解析。
    request.HTTPBody = [@"q=今天天气很好&output=zh_en&format=json&authkey=b0aa5ef944514793812734e0b36e5740" dataUsingEncoding:NSUTF8StringEncoding];
    [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * response, NSData * data, NSError * connectionError) {
        NSLog(@"conncetionError:%@",connectionError);
        NSLog(@"string:%@",[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
        //使用SBJson方法解析
        SBJsonParser *sbJsonParse = [[SBJsonParser alloc] init];
        NSDictionary *dictionary = [sbJsonParse objectWithData:data];
        NSLog(@"dictionary:%@",dictionary);
    }];
}

过期了,没能正确翻译。

2016-09-09 17:12:52.218 JSON解析[985:995210] conncetionError:(null)
2016-09-09 17:12:52.220 JSON解析[985:995210] string:{"status":200,"message":"OK","data":[{"dst":"旧服务已下线,请迁移至 http://api.fanyi.baidu.com","src":"The previous service has been closed, please visit http://api.fanyi.baidu.com to apply for new service."}]}
2016-09-09 17:12:52.223 JSON解析[985:995210] dictionary:{
    data =     (
                {
            dst = "\U65e7\U670d\U52a1\U5df2\U4e0b\U7ebf\Uff0c\U8bf7\U8fc1\U79fb\U81f3 http://api.fanyi.baidu.com";
            src = "The previous service has been closed, please visit http://api.fanyi.baidu.com to apply for new service.";
        }
    );
    message = OK;
    status = 200;
}

4 使用TouchJson解析

解析需要引入头文件

#import "CJSONDeserializer.h"

转换某对象到JSON数据——即生成,序列化操作
需要
引入文件:

#import "CJSONDataserializer.h"

-(void)TouchJsonParse{
    NSURL *url = [NSURL URLWithString:@"http://api.36wu.com/Bus/GetLineInfo"];
    NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url];
    request.HTTPMethod = @"POST";
    //公交查询  一天就过期了这个key值
    request.HTTPBody = [@"city=北京&line=21&format=json&authkey=b0aa5ef944514793812734e0b36e5740" dataUsingEncoding:NSUTF8StringEncoding];
    [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * response, NSData * data, NSError * connectionError) {
        NSLog(@"conncetionError:%@",connectionError);
        NSLog(@"string:%@",[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
        //使用TouchJson解析
        NSDictionary *dictionary = [[CJSONDeserializer deserializer] deserialize:data error:nil];
        NSLog(@"dictionary:%@",dictionary);
    }];
}

该查询数据很长,就不全贴出来了。

{"name":"21路(北京西站-安华桥北)","info":"北京西站北广场5:00-23:00|安华桥北5:00-23:00 ;10公里以内票价2元,每增加5公里以内加价1元,最高票价4元。持卡乘车普通卡5折、学生卡2.5折优惠。","stats":"北京西站;北京世纪坛医院;皇亭子;军事博物馆;木樨地西;木樨地北;西城桥北5:00-23:00 ;10公里以内票价2元,每增加5公里以内加价1元,最高票价4元。持卡乘车普通卡5折、学生卡2.5折优惠。","stats":"北京西站;北京世纪坛医院;皇亭子;军事博物馆;木樨地西;木樨地北;西城\344\270三里河;三里河东口;二七剧场路北口;儿童医院路口西;月坛体育场;阜成门南;阜成门北;西直门南;索家坟;文慧桥北;明光桥北;蓟门桥;蓟门桥北;塔院小区南门;牡丹园西;牡丹园东;健德门桥西;健德门桥桥北5:00-23:00 ;10公里以内票价2元,每增加5公里以内加价1元,最高票价4元。持卡乘车普通卡5折、学生卡2.5折优惠。","stats":"北京西站;北京世纪坛医院;皇亭子;军事博物馆;木樨地西;木樨地北;西城\344\270三里河;三里河东口;二七剧场路北口;儿童医院路口西;月坛体育场;阜成门南;阜成门北;西直门南;索家坟;文慧桥北;明光桥北;蓟门桥;蓟门桥北;塔院小区南门;牡丹园西;牡丹园东;健德门桥西;健德门桥\344东;地铁北土城站;安贞西里;安华桥北"}



本文由http://blog.csdn.net/vnanyesheshou原创,欢迎转载分享。请尊重作者劳动,转载时保留该声明和作者博客链接,谢谢!

作者:VNanyesheshou 发表于2016/9/9 21:10:11 原文链接
阅读:133 评论:0 查看评论

Android安全加密:对称加密与非对称加密

$
0
0

凯撒密码

1. 介绍

凯撒密码作为一种最为古老的对称加密体制,在古罗马的时候都已经很流行,他的基本思想是:通过把字母移动一定的位数来实现加密和解密。明文中的所有字母都在字母表上向后(或向前)按照一个固定数目进行偏移后被替换成密文。例如,当偏移量是3 的时候,所有的字母A 将被替换成D,B 变成E,由此可见,位数就是凯撒密码加密和解密的密钥。

例如:字符串”ABC”的每个字符都右移3 位则变成”DEF”,解密的时候”DEF”的每个字符左移3 位即能还原,如下图所示:

这里写图片描述

2. 准备知识

 //字符转换成ASCII 码数值
 char charA = 'a';
 int intA = charA; //char 强转为int 即得到对应的ASCII 码值,’a’的值为97

//ASCII 码值转成char
int intA = 97;//97 对应的ASCII 码’a’
char charA = (char) intA; //int 值强转为char 即得到对应的ASCII 字符,即'a'

这里写图片描述

3. 凯撒密码的简单代码实现

    /**
     * 加密
     * @param input 数据源(需要加密的数据)
     * @param key 秘钥,即偏移量
     * @return 返回加密后的数据
     */
    public static String encrypt(String input, int key) {
        //得到字符串里的每一个字符
        char[] array = input.toCharArray();

        for (int i = 0; i < array.length; ++i) {
            //字符转换成ASCII 码值
            int ascii = array[i];
            //字符偏移,例如a->b
            ascii = ascii + key;
            //ASCII 码值转换为char
            char newChar = (char) ascii;
            //替换原有字符
            array[i] = newChar;

            //以上4 行代码可以简写为一行
            //array[i] = (char) (array[i] + key);
        }

        //字符数组转换成String
        return new String(array);
    }

    /**
     * 解密
     * @param input 数据源(被加密后的数据)
     * @param key 秘钥,即偏移量
     * @return 返回解密后的数据
     */
    public static String decrypt(String input, int key) {
        //得到字符串里的每一个字符
        char[] array = input.toCharArray();
        for (int i = 0; i < array.length; ++i) {
            //字符转换成ASCII 码值
            int ascii = array[i];
            //恢复字符偏移,例如b->a
            ascii = ascii - key;
            //ASCII 码值转换为char
            char newChar = (char) ascii;
            //替换原有字符
            array[i] = newChar;

            //以上4 行代码可以简写为一行
            //array[i] = (char) (array[i] - key);
        }

        //字符数组转换成String
        return new String(array);
    }

代码输出结果:
这里写图片描述

4. 破解凯撒密码:频率分析法

凯撒密码加密强度太低,只需要用频度分析法即可破解。
在任何一种书面语言中,不同的字母或字母组合出现的频率各不相同。而且,对于以这种语言书写的任意一段文本,都具有大致相同的特征字母分布。比如,在英语中,字母E 出现的频率很高,而X 则出现得较少。

英语文本中典型的字母分布情况如下图所示:
这里写图片描述

5. 破解流程

  • 统计密文里出现次数最多的字符,例如出现次数最多的字符是是’h’。
  • 计算字符’h’到’e’的偏移量,值为3,则表示原文偏移了3 个位置。
  • 将密文所有字符恢复偏移3 个位置。

注意点:统计密文里出现次数最多的字符时,需多统计几个备选,因为最多的可能是空格或者其他字符,例如下图出现次数最多的字符’#’是空格加密后的字符,’h’才是’e’偏移后的值。
这里写图片描述

解密时要多几次尝试,因为不一定出现次数最多的字符就是我们想要的目标字符,如下图,第二次解密的结果才是正确的。

/**
 * 频率分析法破解凯撒密码
 */
public class FrequencyAnalysis {
    //英文里出现次数最多的字符
    private static final char MAGIC_CHAR = 'e';
    //破解生成的最大文件数
    private static final int DE_MAX_FILE = 4;

    public static void main(String[] args) throws Exception {
        //测试1,统计字符个数
        //printCharCount("article1_en.txt");

        //加密文件
        //int key = 3;
        //encryptFile("article1.txt", "article1_en.txt", key);

        //读取加密后的文件
        String artile = file2String("article1_en.txt");
        //解密(会生成多个备选文件)
        decryptCaesarCode(artile, "article1_de.txt");
    }

    public static void printCharCount(String path) throws IOException{
        String data = file2String(path);
        List<Entry<Character, Integer>> mapList = getMaxCountChar(data);
        for (Entry<Character, Integer> entry : mapList) {
            //输出前几位的统计信息
            System.out.println("字符'" + entry.getKey() + "'出现" + entry.getValue() + "次");
        }
    }

    public static void encryptFile(String srcFile, String destFile, int key) throws IOException {
        String artile = file2String(srcFile);
        //加密文件
        String encryptData = MyEncrypt.encrypt(artile, key);
        //保存加密后的文件
        string2File(encryptData, destFile);
    }

    /**
     * 破解凯撒密码
     * @param input 数据源
     * @return 返回解密后的数据
     */
    public static void decryptCaesarCode(String input, String destPath) {
        int deCount = 0;//当前解密生成的备选文件数
        //获取出现频率最高的字符信息(出现次数越多越靠前)
        List<Entry<Character, Integer>> mapList = getMaxCountChar(input);
        for (Entry<Character, Integer> entry : mapList) {
            //限制解密文件备选数
            if (deCount >= DE_MAX_FILE) {
                break;
            }

            //输出前几位的统计信息
            System.out.println("字符'" + entry.getKey() + "'出现" + entry.getValue() + "次");

            ++deCount;
            //出现次数最高的字符跟MAGIC_CHAR的偏移量即为秘钥
            int key = entry.getKey() - MAGIC_CHAR;
            System.out.println("猜测key = " + key + ", 解密生成第" + deCount + "个备选文件" + "\n");
            String decrypt = MyEncrypt.decrypt(input, key);

            String fileName = "de_" + deCount + destPath;
            string2File(decrypt, fileName);
        }
    }

    //统计String里出现最多的字符
    public static List<Entry<Character, Integer>> getMaxCountChar(String data) {
        Map<Character, Integer> map = new HashMap<Character, Integer>();
        char[] array = data.toCharArray();
        for (char c : array) {
            if(!map.containsKey(c)) {
                map.put(c, 1);
            }else{
                Integer count = map.get(c);
                map.put(c, count + 1);
            }
        }

        //输出统计信息
        /*for (Entry<Character, Integer> entry : map.entrySet()) {
            System.out.println(entry.getKey() + "出现" + entry.getValue() +  "次");
        }*/

        //获取获取最大值
        int maxCount = 0;
        for (Entry<Character, Integer> entry : map.entrySet()) {
            //不统计空格
            if (/*entry.getKey() != ' ' && */entry.getValue() > maxCount) { 
                maxCount = entry.getValue();
            }
        }

        //map转换成list便于排序
        List<Entry<Character, Integer>> mapList = new ArrayList<Map.Entry<Character,Integer>>(map.entrySet());
        //根据字符出现次数排序
        Collections.sort(mapList, new Comparator<Entry<Character, Integer>>(){
            @Override
            public int compare(Entry<Character, Integer> o1,
                    Entry<Character, Integer> o2) {
                return o2.getValue().compareTo(o1.getValue());
            }
        });
        return mapList;
    }

    public static String file2String(String path) throws IOException {
        FileReader reader = new FileReader(new File(path));
        char[] buffer = new char[1024];
        int len = -1;
        StringBuffer sb = new StringBuffer();
        while ((len = reader.read(buffer)) != -1) {
            sb.append(buffer, 0, len);
        }
        return sb.toString();
    }

    public static void string2File(String data, String path){
        FileWriter writer = null;
        try {
            writer = new FileWriter(new File(path));
            writer.write(data);
        } catch (Exception e) {
            e.printStackTrace();
        }finally {
            if (writer != null) {
                try {
                    writer.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }

    }
}

这里写图片描述

对称加密

介绍

加密和解密都使用同一把秘钥,这种加密方法称为对称加密,也称为单密钥加密。
简单理解为:加密解密都是同一把钥匙。
凯撒密码就属于对称加密,他的字符偏移量即为秘钥。

对称加密常用算法

AES、DES、3DES、TDEA、Blowfish、RC2、RC4、RC5、IDEA、SKIPJACK 等。

DES:全称为Data Encryption Standard,即数据加密标准,是一种使用密钥加密的块算法,1976 年被美国联邦政府的国家标准局确定为联邦资料处理标准(FIPS),随后在国际上广泛流传开来。

3DES:也叫Triple DES,是三重数据加密算法(TDEA,Triple Data Encryption Algorithm)块密码的通称。
它相当于是对每个数据块应用三次DES 加密算法。由于计算机运算能力的增强,原版DES 密码的密钥长度变得容易被暴力破解;3DES 即是设计用来提供一种相对简单的方法,即通过增加DES 的密钥长度来避免类似的攻击,而不是设计一种全新的块密码算法。

AES: 高级加密标准(英语:Advanced Encryption Standard,缩写:AES),在密码学中又称Rijndael 加密法,是美国联邦政府采用的一种区块加密标准。这个标准用来替代原先的DES,已经被多方分析且广为全世界所使用。经过五年的甄选流程,高级加密标准由美国国家标准与技术研究院(NIST)于2001 年11 月26 日发布于FIPS PUB 197,并在2002 年5 月26 日成为有效的标准。2006 年,高级加密标准已然成为对称密钥加密中最流行的算法之一。

DES 算法简介

DES 加密原理(对比特位进行操作,交换位置,异或等等,无需详细了解)

准备知识

Bit 是计算机最小的传输单位。以0 或1 来表示比特位的值
例如数字3 对应的二进制数据为:00000011

代码示例

 int i = 97;
 String bit = Integer.toBinaryString(i);
 //输出:97 对应的二进制数据为: 1100001
 System.out.println(i + "对应的二进制数据为: " + bit);

Byte 与Bit 区别

数据存储是以“字节”(Byte)为单位,数据传输是以大多是以“位”(bit,又名“比特”)为单位,一个位就代表一个0 或1(即二进制),每8 个位(bit,简写为b)组成一个字节(Byte,简写为B),是最小一级的信息单位。

Byte 的取值范围:

//byte 的取值范围:-128 到127
System.out.println(Byte.MIN_VALUE + "到" + Byte.MAX_VALUE);

即10000000 到01111111 之间,一个字节占8 个比特位

二进制转十进制图示:
这里写图片描述

任何字符串都可以转换为字节数组

String data = "1234abcd";
byte[] bytes = data.getBytes();//内容为:49 50 51 52 97 98 99 100

上面数据49 50 51 52 97 98 99 100 对应的二进制数据(即比特位为):
00110001
00110010
00110011
00110100
01100001
01100010
01100011
01100100

将他们间距调大一点,可看做一个矩阵:
0 0 1 1 0 0 0 1
0 0 1 1 0 0 1 0
0 0 1 1 0 0 1 1
0 0 1 1 0 1 0 0
0 1 1 0 0 0 0 1
0 1 1 0 0 0 1 0
0 1 1 0 0 0 1 1
0 1 1 0 0 1 0 0

之后可对他们进行各种操作,例如交换位置、分割、异或运算等,常见的加密方式就是这样操作比特位的,例如下图的IP 置换以及S-Box 操作都是常见加密的一些方式:

作者:axi295309066 发表于2016/9/9 22:46:57 原文链接
阅读:51 评论:0 查看评论

Android设置item的行间距,以及去掉分割线方法

$
0
0



1.设置item的行间距:
可以在xml布局文件中的listView下设置xml属性:
android:divider="#00000000"
android:dividerHeight="18dp"
解释:分隔线透明,高度为18dp。




2.去掉item之间的分割线:
每个item之间都有分割线,如果单纯想去掉分割线,方法还是很多的:
法1:设置android:divider="@null"
法2:android:divider="@00000000" 后两个0标识透明
法3:setDividerHeight(0);高度设为0
作者:qq_32059827 发表于2016/9/9 22:59:35 原文链接
阅读:55 评论:0 查看评论

Ecilpse中单元测试的使用

$
0
0


Eclipse上的单元测试使用步骤

  • 方法1

1.新建一个 Andoird Test Project

2.输入项目名称后在已有工程下选择一个要测试的工程进行关联,点击finish。



3.这个时候打开AndroidMainifest,会发现多出以下两个代码块,一个是引用库,一个是你目标工程的包名。



4.新建一个类继承AndroidTestCase



5.创建一个方法,这个时候你就可以在里面写自己的测试代码了,而且写要测试类下的方法或是包名也是可以的,因为已经关联了在一起了。



6.对着要测试的方法右键,点击 Android Junit Test 就可以运行了。



7.成功运行后,会去到Junit的界面



LogCat显示结果


  • 方法2

1.把方法1中第三步的红框内代码复制到自己要测试的项目中,写一个类继承AndroidTestCase。



2.编写测试方法和测试的代码



3.测试方式也跟方法1中的第六步一样。

Eclipse上的单元测试使用步骤

  • 方法1

1.新建一个 Andoird Test Project

2.输入项目名称后在已有工程下选择一个要测试的工程进行关联,点击finish。


3.这个时候打开AndroidMainifest,会发现多出以下两个代码块,一个是引用库,一个是你目标工程的包名。


4.新建一个类继承AndroidTestCase


5.创建一个方法,这个时候你就可以在里面写自己的测试代码了,而且写要测试类下的方法或是包名也是可以的,因为已经关联了在一起了。


6.对着要测试的方法右键,点击 Android Junit Test 就可以运行了。



7.成功运行后,会去到Junit的界面


LogCat显示结果


  • 方法2

1.把方法1中第三步的红框内代码复制到自己要测试的项目中,写一个类继承AndroidTestCase。


2.编写测试方法和测试的代码


3.测试方式也跟方法1中的第六步一样。

作者:u011070603 发表于2016/9/10 0:56:25 原文链接
阅读:46 评论:0 查看评论

Android 消息处理机制2(从源码分析)

$
0
0

跟随着上篇 Android 消息处理机制1(从源码分析),下面介绍 “猪脚光环的” : Handler 、Message 、MessageQueue Looper。并以Java 程序模拟安卓的消息处理机制

Handler 在前面已经介绍过了,从创建Handler 实例顺藤摸瓜…

Handler 原理

  1. Handler 封装了消息的发送 (— > 发给谁) 【默认指向自己】
  2. Handler 的依赖对象 Looper 意为:轮询 . 其内部包含了一个消息队列也就是 MessageQueue ,MessageQueue 封装了消息( Message)的载体 所有Handler 发送的信息都走向这个消息队列

两大用途

There are two main uses for a Handler: (1) to schedule messages and runnables to be executed as some point in the future; and (2) to enqueue an action to be performed on a different thread than your own.

Handler 的源码分析

...
public Handler() {
        if (FIND_POTENTIAL_LEAKS) {
            final Class<? extends Handler> klass = getClass();
            if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) &&
                    (klass.getModifiers() & Modifier.STATIC) == 0) {
                Log.w(TAG, "The following Handler class should be static or leaks might occur: " +
                    klass.getCanonicalName());
            }
        }
        mLooper = Looper.myLooper(); //进行关联
        if (mLooper == null) {
            throw new RuntimeException(
                "Can't create handler inside thread that has not called Looper.prepare()");
        }
        mQueue = mLooper.mQueue;
        mCallback = null;
    }

    ...

由源码得出:

Post:Post允许把一个Runnable对象入队到消息队列中。它的方法有:post(Runnable),postAtTime(Runnable,long),postDelayed(Runnable,long).
sendMessage:sendMessage允许把一个包含消息数据的Message对象压入到消息队列中。它的方法有:sendEmptyMessage(int), sendMessage(Message).sendMessageAtTime(Message,long).sendMessageDelayed(Message,long)。
  从上面的各种方法可以看出,不管是post还是sendMessage都具有多种方法,它们可以设定Runnable对象和Message对象被入队到消息队列中,是立即执行还是延迟执行。

Looper 原理

本质是一个死循环 不断地从 MessageQueue 中取出数据,有消息就取出,没消息就阻塞。

Looper中重要的方法:

static void loop()
Run the message queue in this thread.

为什么Handler 内部要与 Looper 进行关联?

不关联Handler 如何向MessageQueue 发送Message呢

总的来说: Handler 负责发送消息,Looper 负责接收消息并把消息回传给 Handler , 而 MessageQueue 是就是存储 Message 的容器

Framework 源码简析

UI 线程 ActivityThread 创建 Looper Message

这里写图片描述


这里写图片描述


这里写图片描述


new Looper(); 后做了那些操作呢?

这里写图片描述

如何取出 当前线程关联的 Looper 对象?

public static Looper myLooper() {
        return sThreadLocal.get();
}

Handler 发送消息到 MessageQueue (消息入列)

这里写图片描述

Handler取出 当前线程关联的 Looper 对象 是为了Looper 中MessageQueue 对象进行发送消息Message

Tips:对于Message对象,一般并不推荐直接使用它的构造方法得到,而是建议通过使用Message.obtain()这个静态的方法或者Handler.obtainMessage()获取。Message.obtain()会从消息池中获取一个Message对象,如果消息池中是空的,才会使用构造方法实例化一个新Message,这样有利于消息资源的利用。并不需要担心消息池中的消息过多,它是有上限的,上限为10个。Handler.obtainMessage()具有多个重载方法,如果查看源码,会发现其实Handler.obtainMessage()在内部也是调用的Message.obtain()。  

Java 程序实现

下面代码由 Framework 源码拷贝出来进行分析,每一位安卓工程师都应该拥有一份 Framework 源码,以便了解android.

ActivityThread (程序入口)

public class ActivityThread {

    public static void main(String[] args) {
        //初始化主线程的 Looper 对象
        Looper.prepareMainLooper();
        final Handler handler = new Handler() {
            @Override
            public void handleMessage(Message msg) {
                super.handleMessage(msg);
                System.out.println("接收到 what = " + msg.what);
                System.out.println("Thread " + Thread.currentThread().getName());
            }
        };
        handler.sendEmptyMessage(1);
        handler.sendEmptyMessage(2);
        new Thread(new Runnable() {
            @Override
            public void run() {
                handler.sendEmptyMessage(1001);
                try {
                    Thread.sleep(6000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                //子线程 通过Handler 发送消息到主线程的消息队列, 主线程处理该消息
                handler.sendEmptyMessage(1001);
            }
        }).start();

        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    Thread.sleep(3000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

                handler.sendEmptyMessage(1000);
                handler.sendEmptyMessage(1000);
                handler.sendEmptyMessage(1000);
                handler.sendEmptyMessage(1000);
                handler.sendEmptyMessage(1000);

                //初始化 Looper
                Looper.prepare();
                final Handler handler = new Handler() {
                    @Override
                    public void handleMessage(Message msg) {
                        super.handleMessage(msg);
                        //子线程
                        System.out.println("接收到 what = " + msg.what);
                        System.out.println("Thread " + Thread.currentThread().getName());
                    }
                };

                handler.sendEmptyMessage(999);
                handler.sendEmptyMessage(9999);
                //轮询
                Looper.loop();
            }
        }).start();
        //轮询
        Looper.loop();
    }
}

Handler 代码

package android.os;

/**
 * Created by system on 16/9/6.
 * <p>
 * 处理和分发消息
 *
 */
public class Handler {

    final MessageQueue mQueue;
    final Looper mLooper;

    public Handler() {
        mLooper = Looper.myLooper();
        if (mLooper == null) {
            throw new RuntimeException(
                    "Can't create handler inside thread that has not called Looper.prepare()");
        }
        mQueue = mLooper.mQueue;
    }


    public void handleMessage(Message msg) {
    }

    /**
     * Handle system messages here.
     */
    public void dispatchMessage(Message msg) {
        if (msg != null) {
            handleMessage(msg);
        }
    }

    public final boolean sendEmptyMessage(int what) {
        Message msg = new Message();
        msg.what = what;
        MessageQueue queue = mQueue;
        if (queue == null) {
            RuntimeException e = new RuntimeException(
                    this + " sendMessageAtTime() called with no mQueue");
            System.out.println(e.getMessage());
            return false;
        }
        msg.target = this;
        return queue.enqueueMessage(msg);
    }

}

Looper

package android.os;

/**
 * Created by system on 16/9/6.
 *
 *
 * 每开启一条线程都应为之创建一个与该线程绑定 Looper 对象 ,以及 MessageQueue 队列
 */
public class Looper {

    static final ThreadLocal<Looper> sThreadLocal = new ThreadLocal<Looper>();
    private static Looper sMainLooper;  // guarded by Looper.class

    final MessageQueue mQueue;
    final Thread mThread;

    private Looper() {
        mQueue = new MessageQueue();
        mThread = Thread.currentThread();
    }

    public static void prepare() {
        if (sThreadLocal.get() != null) {
            throw new RuntimeException("Only one Looper may be created per thread");
        }
        sThreadLocal.set(new Looper());
    }

    public static void prepareMainLooper() {
        prepare();
        synchronized (Looper.class) {
            if (sMainLooper != null) {
                throw new IllegalStateException("The main Looper has already been prepared.");
            }
            sMainLooper = myLooper();
        }
    }

    public static Looper myLooper() {
        return sThreadLocal.get();
    }

    public static void loop() {
        final Looper me = myLooper();
        if (me == null) {
            throw new RuntimeException("No Looper; Looper.prepare() wasn't called on this thread.");
        }
        final MessageQueue queue = me.mQueue;

        // Make sure the identity of this thread is that of the local process,
        // and keep track of what that identity token actually is.

        for (;;) {
            Message msg = queue.next(); // might block
            if (msg == null) {
                // No message indicates that the message queue is quitting.
                return;
            }

            //分发消息
            msg.target.dispatchMessage(msg);


        }
    }
}

Message

package android.os;

/**
 * Created by system on 16/9/6.
 *  消息
 *  由MessageQueue统一列队,终由Handler处理。
 */
public class Message {

    public int what;

    /*package*/ Handler target;

    /*package*/ Runnable callback;

    // sometimes we store linked lists of these things
    /*package*/ Message next;


}

MessageQueue

package android.os;

/**
 * Created by system on 16/9/6.
 *
 * 消息队列,用来存放Handler发送过来的消息(Message),并按照FIFO规则执行
 * note:(将Message以链表的方式串联起来的,等待Looper的轮询)
 */
public class MessageQueue {
    Message mMessages;// 当前消息
    private static final Object lock = new Object();

    /**
     * 出列 FO (即取出队头的消息)
     * @return Message
     */
    Message next() {
        //没有消息时 阻塞
        for (; ; ) {
            synchronized (this) {
                Message prevMsg = null;
                Message msg = mMessages;
                if (msg != null && msg.target == null) {
                    // Stalled by a barrier.  Find the next asynchronous message in the queue.
                    do {
                        prevMsg = msg;
                        msg = msg.next;
                    } while (msg != null);
                }
                if (msg != null) {

                    if (prevMsg != null) {
                        prevMsg.next = msg.next;
                    } else {
                        mMessages = msg.next; //成为队头
                    }
                    msg.next = null; //remove
                    return msg;
                }

            }
        }
    }

    /**
     * 消息入列  FIFO
     * @param msg
     * @return
     */
    boolean enqueueMessage(Message msg) {
        if (msg.target == null) {
            throw new IllegalArgumentException("Message must have a target.");
        }
        synchronized (this) {

            Message p = mMessages;

            if (p == null) {
                // New head, wake up the event queue if blocked.
                msg.next = p;
                mMessages = msg;

            } else {
                Message prev;
                for (; ; ) {
                    prev = p;
                    p = p.next;
                    if (p == null) {
                        break;
                    }

                }
                msg.next = p; // invariant: p == prev.next
                prev.next = msg; //成为链尾
            }

        }
        return true;
    }
}

运行效果图:
这里写图片描述

代码下载

更详细的Android 消息处理机制分析,请看 Android 消息处理机制

作者:CSDNno 发表于2016/9/10 21:34:04 原文链接
阅读:68 评论:0 查看评论

深入理解ButterKnife源码并掌握原理(一)

$
0
0

前言

话说在android这座大山里,有一座庙(方块公司-square),庙里住着一个神-jake(我是这么叫的嘻嘻)。
不要小看这个小jake,这个神可是为android应用开发们提供了强有力的帮助。比如流行的开源库okhttp,eventbus系列 ,retrofit,butterknife 等等都是出于他之手。小弟佩服的不要不要的…,可以说是为android的应用开发效率和耦合性提高了一个台阶啊。
其它的大神我也是佩服的不要不要的…嘻嘻

声明

这一系列的文章是对ButterKnife的源码进行分析的,涉及的细节比较多,但也比较广。一次看不懂no 问题,慢慢来嘛,嘻嘻
如有不对的地方,还望指导。
最后会给出自己实现的一个demo,主要是原理和思想哦!!!

代码结构

代码结构
我们这里对ButterKnife的最新版本8.4.0进行分析。
我们先down下来看下代码的结构,可以看到代码结构分的还是很好的。

  • butterknife ;android library model 提供android使用的API
  • butterknife-annotations; java-model,使用时的注解
  • butterknife-compiler;java-model,编译时用到的注解的处理器
  • butterknife-gradle-plugin;自定义的gradle插件,辅助生成有关代码
  • butterknife-integration-test;该项目的测试用例
  • butterknife-lint;该项目的lint检查
  • sample;demo

可以看到大神的代码很风骚的,很清晰啊。
这里重点分析butterknife-compiler及butterknife model

原理图

你可以看完了再回来看这个图,会更明白。
butterKnife框架图
butterKnife原理图

使用方法

这里不再给出。不过会在原代码分析的时候给出一些注意的地方。
我们拿官方的demo-SimpleActivity
编译完后最后生成的文件为:SimpleActivity_ViewBinding
路径在:
生成的文件
内容:

// Generated code from Butter Knife. Do not modify!
package com.example.butterknife.library;

import android.support.annotation.CallSuper;
import android.support.annotation.UiThread;
import android.view.View;
import android.widget.AdapterView;
import android.widget.Button;
import android.widget.ListView;
import android.widget.TextView;
import butterknife.Unbinder;
import butterknife.internal.DebouncingOnClickListener;
import butterknife.internal.Utils;
import java.lang.IllegalStateException;
import java.lang.Override;

public class SimpleActivity_ViewBinding<T extends SimpleActivity> implements Unbinder {
  protected T target;

  private View view2130968578;

  private View view2130968579;

  @UiThread
  public SimpleActivity_ViewBinding(final T target, View source) {
    this.target = target;

    View view;
    target.title = Utils.findRequiredViewAsType(source, R.id.title, "field 'title'", TextView.class);
    target.subtitle = Utils.findRequiredViewAsType(source, R.id.subtitle, "field 'subtitle'", TextView.class);
    view = Utils.findRequiredView(source, R.id.hello, "field 'hello', method 'sayHello', and method 'sayGetOffMe'");
    target.hello = Utils.castView(view, R.id.hello, "field 'hello'", Button.class);
    view2130968578 = view;
    view.setOnClickListener(new DebouncingOnClickListener() {
      @Override
      public void doClick(View p0) {
        target.sayHello();
      }
    });
    view.setOnLongClickListener(new View.OnLongClickListener() {
      @Override
      public boolean onLongClick(View p0) {
        return target.sayGetOffMe();
      }
    });
    view = Utils.findRequiredView(source, R.id.list_of_things, "field 'listOfThings' and method 'onItemClick'");
    target.listOfThings = Utils.castView(view, R.id.list_of_things, "field 'listOfThings'", ListView.class);
    view2130968579 = view;
    ((AdapterView<?>) view).setOnItemClickListener(new AdapterView.OnItemClickListener() {
      @Override
      public void onItemClick(AdapterView<?> p0, View p1, int p2, long p3) {
        target.onItemClick(p2);
      }
    });
    target.footer = Utils.findRequiredViewAsType(source, R.id.footer, "field 'footer'", TextView.class);
    target.headerViews = Utils.listOf(
        Utils.findRequiredView(source, R.id.title, "field 'headerViews'"), 
        Utils.findRequiredView(source, R.id.subtitle, "field 'headerViews'"), 
        Utils.findRequiredView(source, R.id.hello, "field 'headerViews'"));
  }

  @Override
  @CallSuper
  public void unbind() {
    T target = this.target;
    if (target == null) throw new IllegalStateException("Bindings already cleared.");

    target.title = null;
    target.subtitle = null;
    target.hello = null;
    target.listOfThings = null;
    target.footer = null;
    target.headerViews = null;

    view2130968578.setOnClickListener(null);
    view2130968578.setOnLongClickListener(null);
    view2130968578 = null;
    ((AdapterView<?>) view2130968579).setOnItemClickListener(null);
    view2130968579 = null;

    this.target = null;
  }
}

我们看到了我们熟悉的代码,虽然比较乱(因为是生成的),
可以看出 在构造中findview 在unbind中进行置null处理,让告诉gc在合适的机会回收占用的内存 ;但是这是后面真正生成代码我们看不到的,没关系 嘻嘻。

整体的原理-(编译时期-注解处理器)

在java代码的编译时期,javac 会调用java注解处理器来进行处理。因此我们可以定义自己的注解处理器来干一些事情。一个特定注解的处理器以 java 源代码(或者已编译的字节码)作为输入,然后生成一些文件(通常是.java文件)作为输出。因此我们可以在用户已有的代码上添加一些方法,来帮我们做一些有用的事情。这些生成的 java 文件跟其他手动编写的 java 源代码一样,将会被 javac 编译。(个人参考及个人理解)

定义处理器 继承AbstractProcessor

在java中定义自己的处理器都是继承自AbstractProcessor
前3个方法都试固定写法,主要是process方法。

public class MyProcessor extends AbstractProcessor {

    //用来指定你使用的 java 版本。通常你应该返回                                SourceVersion.latestSupported()

    @Override
    public SourceVersion getSupportedSourceVersion() {
        return SourceVersion.latestSupported();
    }

    //会被处理器调用,可以在这里获取Filer,Elements,Messager等辅助类,后面会解释
    @Override
    public synchronized void init(ProcessingEnvironment processingEnv) {
        super.init(processingEnv);
    }


//这个方法返回stirng类型的set集合,集合里包含了你需要处理的注解
    @Override
    public Set<String> getSupportedAnnotationTypes() {
        Set<String> annotataions = new LinkedHashSet<String>();
        annotataions.add("com.example.MyAnnotation");
        return annotataions;
    }


   //核心方法,这个一般的流程就是先扫描查找注解,再生成 java 文件
   //这2个步骤设计的知识点细节很多。

    @Override
    public boolean process(Set<? extends TypeElement> annoations,
            RoundEnvironment env) {
        return false;
    }
}

注册你的处理器

要像jvm调用你写的处理器,你必须先注册,让他知道。怎么让它知道呢,其实很简单,google 为我们提供了一个库,简单的一个注解就可以。
首先是依赖

  compile 'com.google.auto.service:auto-service:1.0-rc2'
@AutoService(Processor.class)
public class BindViewProcessor extends AbstractProcessor {
  //...省略非关键代码

基本概念

  • Elements:一个用来处理Element的工具类
  • Types:一个用来处理TypeMirror的工具类
  • Filer:你可以使用这个类来创建.java文件

源码分析

分析之前呢先要有写基本的概念

可以看到AutoService注解

@AutoService(Processor.class)
public final class ButterKnifeProcessor extends AbstractProcessor {
//...
(1)init 方法,这个主要是获取一些辅助类
    private Filer mFiler; //文件相关的辅助类
    private Elements mElementUtils; //元素相关的辅助类
    private Messager mMessager; //日志相关的辅助类

  @Override public synchronized void init(ProcessingEnvironment env) {
    super.init(env);

    elementUtils = env.getElementUtils();
    typeUtils = env.getTypeUtils();
    filer = env.getFiler();
    try {
      trees = Trees.instance(processingEnv);
    } catch (IllegalArgumentException ignored) {
    }
  }
(2)getSupportedSourceVersion()方法就是默认的,获取你该处理器使用的java版本
 @Override public SourceVersion getSupportedSourceVersion() {
    return SourceVersion.latestSupported();
  }
(4)接下来就是process方法,这个方法是核心方法。
 @Override public boolean process(Set<? extends TypeElement> elements, RoundEnvironment env) {
 //1.查找所有的注解信息,并形成BindingClass(是什么 后面会讲) 保存到 map中
    Map<TypeElement, BindingClass> targetClassMap = findAndParseTargets(env);

//2.遍历步骤1的map 的生成.java文件也就是上文的  类名_ViewBinding  的java文件

  for (Map.Entry<TypeElement, BindingClass> entry : targetClassMap.entrySet()) {
      TypeElement typeElement = entry.getKey();
      BindingClass bindingClass = entry.getValue();

      JavaFile javaFile = bindingClass.brewJava();
      try {
        javaFile.writeTo(filer);
      } catch (IOException e) {
        error(typeElement, "Unable to write binding for type %s: %s", typeElement, e.getMessage());
      }
    }

    return true;
  }

咦,很明显,2步走啊。是的没错, 满满套路啊!!大家都回农村吧,嘻嘻
下面我们仔细走一下该方法流程。

  1. 每个注解的查找与解析-findAndParseTargets
  private Map<TypeElement, BindingClass> findAndParseTargets(RoundEnvironment env) {
    Map<TypeElement, BindingClass> targetClassMap = new LinkedHashMap<>();
    Set<TypeElement> erasedTargetNames = new LinkedHashSet<>();

    scanForRClasses(env);
    //...下面是每个注解的解析
 // Process each @BindArray element.
    for (Element element : env.getElementsAnnotatedWith(BindArray.class)) {
      if (!SuperficialValidation.validateElement(element)) continue;
      try {
        parseResourceArray(element, targetClassMap, erasedTargetNames);
      } catch (Exception e) {
        logParsingError(element, BindArray.class, e);
      }
    }

     // Process each @BindView element.
    for (Element element : env.getElementsAnnotatedWith(BindView.class)) {
      // we don't SuperficialValidation.validateElement(element)
      // so that an unresolved View type can be generated by later processing rounds
      try {
        parseBindView(element, targetClassMap, erasedTargetNames);
      } catch (Exception e) {
        logParsingError(element, BindView.class, e);
      }
    }
   //....


      // Process each annotation that corresponds to a listener.
    for (Class<? extends Annotation> listener : LISTENERS) {
      findAndParseListener(env, listener, targetClassMap, erasedTargetNames);
    }

    // Try to find a parent binder for each.
    for (Map.Entry<TypeElement, BindingClass> entry : targetClassMap.entrySet()) {
      TypeElement parentType = findParentType(entry.getKey(), erasedTargetNames);
      if (parentType != null) {
        BindingClass bindingClass = entry.getValue();
        BindingClass parentBindingClass = targetClassMap.get(parentType);
        bindingClass.setParent(parentBindingClass);
      }
    }

    return targetClassMap;

}

首先我们先看一下参数 RoundEnvironment 这个是什么呢?个人理解是注解框架里的一个工具什么工具呢?一个可以在处理器处理该处理器 用来查询注解信息的工具,当然包含你在getSupportedAnnotationTypes注册的注解。
接下来呢?
创建了一个LinkedHashMap保证了先后的顺序就是先注解的先生成java文件,其实也没有什么先后无所谓。最后将其返回。
我们这里只分析一个具有代表性的BindView注解,其它的都是一样的,连代码都一毛一样。
在这之前先看一下Element这个类我们看一下官方注释

 * Represents a program element such as a package, class, or method.
 * Each element represents a static, language-level construct
 * (and not, for example, a runtime construct of the virtual machine).

在注解处理器中,我们扫描 java 源文件,源代码中的每一部分都是Element的一个特定类型。换句话说:Element代表程序中的元素,比如说 包,类,方法。每一个元素代表一个静态的,语言级别的结构.
比如:

public class ClassA { // TypeElement
    private int var_0; // VariableElement
    public ClassA() {} // ExecuteableElement

    public void setA( // ExecuteableElement
            int newA // TypeElement
    ) {
    }
}

可以看到类为TypeElement,变量为VariableElement,方法为ExecuteableElement
这些都是Element的子类,自己可以看下源码,的确如此的。

TypeElement aClass ;
for (Element e : aClass.getEnclosedElements()){ //获取所有的子节点
    Element parent = e.getEnclosingElement();  // 获取父节点
    }

Elements代表源代码,TypeElement代表源代码中的元素类型,例如类。然后,TypeElement并不包含类的相关信息。你可以从TypeElement获取类的名称,但你不能获取类的信息,比如说父类。这些信息可以通过TypeMirror获取。你可以通过调用element.asType()来获取一个Element的TypeMirror。

这个是对于理解源码的基础。
继续,我们看到了for循环查找所有包含BindView的注解。

 parseBindView(element, targetClassMap, erasedTargetNames);

把element和targetClassMap传入

  private void parseBindView(Element element, Map<TypeElement, BindingClass> targetClassMap,
      Set<TypeElement> erasedTargetNames) {
    TypeElement enclosingElement = (TypeElement) element.getEnclosingElement();

     //1.检查用户使用的合法性
    // Start by verifying common generated code restrictions.
    boolean hasError = isInaccessibleViaGeneratedCode(BindView.class, "fields", element)
        || isBindingInWrongPackage(BindView.class, element);

    // Verify that the target type extends from View.
    TypeMirror elementType = element.asType();
    if (elementType.getKind() == TypeKind.TYPEVAR) {
      TypeVariable typeVariable = (TypeVariable) elementType;
      elementType = typeVariable.getUpperBound();
    }
    if (!isSubtypeOfType(elementType, VIEW_TYPE) && !isInterface(elementType)) {
      if (elementType.getKind() == TypeKind.ERROR) {
        note(element, "@%s field with unresolved type (%s) "
                + "must elsewhere be generated as a View or interface. (%s.%s)",
            BindView.class.getSimpleName(), elementType, enclosingElement.getQualifiedName(),
            element.getSimpleName());
      } else {
        error(element, "@%s fields must extend from View or be an interface. (%s.%s)",
            BindView.class.getSimpleName(), enclosingElement.getQualifiedName(),
            element.getSimpleName());
        hasError = true;
      }
    }

    // 不合法的直接返回
    if (hasError) {
      return;
    }


    //2.获取id 值

    // Assemble information on the field.
    int id = element.getAnnotation(BindView.class).value();

    // 3.获取 BindingClass,有缓存机制, 没有则创建,下文会仔细分析

    BindingClass bindingClass = targetClassMap.get(enclosingElement);
    if (bindingClass != null) {
      ViewBindings viewBindings = bindingClass.getViewBinding(getId(id));
      if (viewBindings != null && viewBindings.getFieldBinding() != null) {
        FieldViewBinding existingBinding = viewBindings.getFieldBinding();
        error(element, "Attempt to use @%s for an already bound ID %d on '%s'. (%s.%s)",
            BindView.class.getSimpleName(), id, existingBinding.getName(),
            enclosingElement.getQualifiedName(), element.getSimpleName());
        return;
      }
    } else {
      bindingClass = getOrCreateTargetClass(targetClassMap, enclosingElement);
    }
   //4 生成FieldViewBinding 实体 

    String name = element.getSimpleName().toString();
    TypeName type = TypeName.get(elementType);
    boolean required = isFieldRequired(element);

    FieldViewBinding binding = new FieldViewBinding(name, type, required);
     //5。加入到 bindingClass 成员变量的集合中
    bindingClass.addField(getId(id), binding);

    // Add the type-erased version to the valid binding         targets set.
    erasedTargetNames.add(enclosingElement);

  }

element.getEnclosingElement();是什么呢?是父节点。就是上面我们说的。
基本的步骤就是上面的5步
1.检查用户使用的合法性

   // Start by verifying common generated code restrictions.
    boolean hasError = isInaccessibleViaGeneratedCode(BindView.class, "fields", element)
        || isBindingInWrongPackage(BindView.class, element);
 private boolean isInaccessibleViaGeneratedCode(Class<? extends Annotation> annotationClass,
      String targetThing, Element element) {
    boolean hasError = false;
    // 得到父节点
    TypeElement enclosingElement = (TypeElement) element.getEnclosingElement();

 //判断修饰符,如果包含private or static 就会抛出异常。
    // Verify method modifiers.
    Set<Modifier> modifiers = element.getModifiers();
    if (modifiers.contains(PRIVATE) || modifiers.contains(STATIC)) {
      error(element, "@%s %s must not be private or static. (%s.%s)",
          annotationClass.getSimpleName(), targetThing, enclosingElement.getQualifiedName(),
          element.getSimpleName());
      hasError = true;
    }

        //判断父节点是否是类类型的,不是的话就会抛出异常
        //也就是说BindView 的使用必须在一个类里
    // Verify containing type.
    if (enclosingElement.getKind() != CLASS) {
      error(enclosingElement, "@%s %s may only be contained in classes. (%s.%s)",
          annotationClass.getSimpleName(), targetThing, enclosingElement.getQualifiedName(),
          element.getSimpleName());
      hasError = true;
    }

     //判断父节点如果是private 类,则抛出异常
    // Verify containing class visibility is not private.
    if (enclosingElement.getModifiers().contains(PRIVATE)) {
      error(enclosingElement, "@%s %s may not be contained in private classes. (%s.%s)",
          annotationClass.getSimpleName(), targetThing, enclosingElement.getQualifiedName(),
          element.getSimpleName());
      hasError = true;
    }

    return hasError;
  }

上面的代码里遇见注释了,这里说一下也就是我们在使用bindview注解的时候不能用使用

 类不能是private修饰 ,可以是默认的或者public 
  //in adapter
   private  static final class ViewHolder {
   //....//成员变量不能是private修饰 ,可以是默认的或者public 
   @BindView(R.id.word)
  private  TextView word;  

接下来还有一个方法isBindingInWrongPackage。
这个看名字也才出来个大概 就是不能在android ,java这种源码的sdk中使用。如果你的包名是以android或者java开头就会抛出异常。

   private boolean isBindingInWrongPackage(Class<? extends Annotation> annotationClass,
      Element element) {
      //得到父节点
    TypeElement enclosingElement = (TypeElement) element.getEnclosingElement();
    String qualifiedName = enclosingElement.getQualifiedName().toString();

    if (qualifiedName.startsWith("android.")) {
      error(element, "@%s-annotated class incorrectly in Android framework package. (%s)",
          annotationClass.getSimpleName(), qualifiedName);
      return true;
    }
    if (qualifiedName.startsWith("java.")) {
      error(element, "@%s-annotated class incorrectly in Java framework package. (%s)",
          annotationClass.getSimpleName(), qualifiedName);
      return true;
    }

    return false;
  } 

到这里合法性检查就完了,如果你使用不当,就会抛出异常。

 // 。。。 异常抛出了
 // 不合法的直接返回
    if (hasError) {
      return;
    }

这里说明一点,在处理器中抛出异常,你不能直接像平常写java代码一样new thow xxx 一样,这样抛出去的异常不太好看。所以java处理器帮我们提供了一个辅助类Messager,这个可以帮助我们

      /**
     * Returns the messager used to report errors, warnings, and other
     * notices.
     *
     * @return the messager
     */
    Messager getMessager();

比如检查使用合法性抛出的异常信息-error方法最后都会调用

  private void error(Element element, String message, Object... args) {
  //Kind.ERROR 级别,就像你使用android的log一样
    printMessage(Kind.ERROR, element, message, args);
  }

  private void note(Element element, String message, Object... args) {
    printMessage(Kind.NOTE, element, message, args);
  }

  private void printMessage(Kind kind, Element element, String message, Object[] args) {
    if (args.length > 0) {
      message = String.format(message, args);
    }

    processingEnv.getMessager().printMessage(kind, message, element);
}

ok,到这里说了这么多才完成了检查。我们接着parseBindView的步骤2 获取值 ,这里就不多说了。好了,先休息下吧…
下一篇我们接着看。
深入理解ButterKnife源码并掌握原理(二)

作者:ta893115871 发表于2016/9/10 22:06:13 原文链接
阅读:48 评论:0 查看评论

深入理解ButterKnife源码并掌握原理(二)

$
0
0

好,我们接着parseBindView的步骤3 ,忘记了在哪里了,咦,可以看下上一篇,哈哈。
步骤3

   BindingClass bindingClass = targetClassMap.get(enclosingElement);
    if (bindingClass != null) {
      ViewBindings viewBindings = bindingClass.getViewBinding(getId(id));
      if (viewBindings != null && viewBindings.getFieldBinding() != null) {
        FieldViewBinding existingBinding = viewBindings.getFieldBinding();
        error(element, "Attempt to use @%s for an already bound ID %d on '%s'. (%s.%s)",
            BindView.class.getSimpleName(), id, existingBinding.getName(),
            enclosingElement.getQualifiedName(), element.getSimpleName());
        return;
      }
    } else {
      bindingClass = getOrCreateTargetClass(targetClassMap, enclosingElement);
    }

如果map(缓存)中已经有了就直接到到这个BindingClass实例。BindingClass这个我们后面还会再说。

1.如果不为空,则根据id获取保存在bindingClass中的ViewBindings实例,
如果viewBindings不为空且viewBindings.getFieldBinding不为空则抛出异常,什么意思呢?就是说一个id不能bind多次。
2.如果为空,则bindingClass = getOrCreateTargetClass(targetClassMap, enclosingElement);
获取并返回,参数是最初的那个map和父节点。

  private BindingClass getOrCreateTargetClass(Map<TypeElement, BindingClass> targetClassMap,
      TypeElement enclosingElement) {
    BindingClass bindingClass = targetClassMap.get(enclosingElement);
    //再次判断
    if (bindingClass == null) {
     //获取父节点的类型名字,这个不用太关系
      TypeName targetType = TypeName.get(enclosingElement.asType());
      if (targetType instanceof ParameterizedTypeName) {
        targetType = ((ParameterizedTypeName) targetType).rawType;
      }

 //获取该enclosingElement就是父节点所在的包名称

      String packageName = getPackageName(enclosingElement);
    //类名字
      String className = getClassName(enclosingElement, packageName);
      //根据包名称和类名称获取bindingClassName实体
      //并且加入了_ViewBinding 哈哈,有点意思是了。不是吗??
      ClassName bindingClassName = ClassName.get(packageName, className + "_ViewBinding");

    //是否是final 类 
      boolean isFinal = enclosingElement.getModifiers().contains(Modifier.FINAL);

//创建了一个BindingClass实例
      bindingClass = new BindingClass(targetType, bindingClassName, isFinal);
      //加入集合,缓存
      targetClassMap.put(enclosingElement, bindingClass);
    }
    return bindingClass;
  }

到此我们的parseBindView的步骤3就完了。
步骤4:parseBindView步骤4


    //@BindView(R.id.word)
    // TextView word;  
    //name就是word
    String name = element.getSimpleName().toString();
     //类型的名字
    TypeName type = TypeName.get(elementType);
    //是否要求可为空
    boolean required = isFieldRequired(element);
     //生成FieldViewBinding实体
    FieldViewBinding binding = new FieldViewBinding(name, type, required);

步骤5.

添加到bindingClass中的成员变量的实体的集合中,方便生成java源文件也就是xxxxx_ViewBinding文件的成员变量的初始化存在
bindingClass.addField(getId(id), binding);

其它的注解都是一样的。至此查找并解析成员变量的流程就完了。
接下来是处理控件事件的监听的流程。

注解事件源码流程分析(OnClick,OnItemClick等)

我们回到findAndParseTargets方法。

   //... 省略成员变量的注解

 // Process each annotation that corresponds to a listener.

    //处理方法的比如一些OnClick,OnItemClick等
    for (Class<? extends Annotation> listener : LISTENERS) {
      findAndParseListener(env, listener, targetClassMap, erasedTargetNames);
    }

    // Try to find a parent binder for each.
    for (Map.Entry<TypeElement, BindingClass> entry : targetClassMap.entrySet()) {
      TypeElement parentType = findParentType(entry.getKey(), erasedTargetNames);
      if (parentType != null) {
        BindingClass bindingClass = entry.getValue();
        BindingClass parentBindingClass = targetClassMap.get(parentType);
        bindingClass.setParent(parentBindingClass);
      }
    }

    return targetClassMap;
   }

处理注解事件同样也分为查找和解析2个大步骤。
LISTENERS是butterknife支持的注解集合

  private static final List<Class<? extends Annotation>> LISTENERS = Arrays.asList(//
      OnCheckedChanged.class, //
      OnClick.class, //
      OnEditorAction.class, //
      OnFocusChange.class, //
      OnItemClick.class, //
      OnItemLongClick.class, //
      OnItemSelected.class, //
      OnLongClick.class, //
      OnPageChange.class, //
      OnTextChanged.class, //
      OnTouch.class //
  );
 private void findAndParseListener(RoundEnvironment env,
      Class<? extends Annotation> annotationClass, Map<TypeElement, BindingClass> targetClassMap,
      Set<TypeElement> erasedTargetNames) {
    for (Element element : env.getElementsAnnotatedWith(annotationClass)) {
     //检查合法性问题
      if (!SuperficialValidation.validateElement(element)) continue;
      try {
         //解析注解
        parseListenerAnnotation(annotationClass, element, targetClassMap, erasedTargetNames);
      } catch (Exception e) {
        StringWriter stackTrace = new StringWriter();
        e.printStackTrace(new PrintWriter(stackTrace));

        error(element, "Unable to generate view binder for @%s.\n\n%s",
            annotationClass.getSimpleName(), stackTrace.toString());
      }
    }
  }

 ```
我们看一下parseListenerAnnotation方法,传入了注解类annotationClass,该节点element,最初的那个集合targetClassMap。
 比较长,我在方法里注释效果会比较好,哈哈

 ```
  private void parseListenerAnnotation(Class<? extends Annotation> annotationClass, Element element,
      Map<TypeElement, BindingClass> targetClassMap, Set<TypeElement> erasedTargetNames)
      throws Exception {
    // This should be guarded by the annotation's @Target but it's worth a check for safe casting.
    //必需是方法类型的,节点元素为ExecutableElement
    if (!(element instanceof ExecutableElement) || element.getKind() != METHOD) {
      throw new IllegalStateException(
          String.format("@%s annotation must be on a method.", annotationClass.getSimpleName()));
    }

//方法对应的是ExecutableElement,前文我们已经简单的说明了一下
    ExecutableElement executableElement = (ExecutableElement) element;
    //获取父节点
    TypeElement enclosingElement = (TypeElement) element.getEnclosingElement();

    // Assemble information on the method.
    // 获取注解信息
    Annotation annotation = element.getAnnotation(annotationClass);
    //该注解value方法,每一个注解都有(butterknife提供的都是数组)
    //为什么是数组?因为支持下面这种
      @OnClick({R.id.hello,R.id.hello2}) 
      void sayHello() {
      }
      //反射注解方法value
    Method annotationValue = annotationClass.getDeclaredMethod("value");
    //不是数组抛出异常
    if (annotationValue.getReturnType() != int[].class) {
      throw new IllegalStateException(
          String.format("@%s annotation value() type not int[].", annotationClass));
    }

    //反射调用
    int[] ids = (int[]) annotationValue.invoke(annotation);
    //方法名字
    String name = executableElement.getSimpleName().toString();
    boolean required = isListenerRequired(executableElement);

    // Verify that the method and its containing class are accessible via generated code.
    //检查方法的修饰符,和成员变量一样,这里就不写了,嘻嘻
    boolean hasError = isInaccessibleViaGeneratedCode(annotationClass, "methods", element);
    hasError |= isBindingInWrongPackage(annotationClass, element);

     //一个注解的方法不能有形同的id,or抛出异常
    Integer duplicateId = findDuplicate(ids);
    if (duplicateId != null) {
      error(element, "@%s annotation for method contains duplicate ID %d. (%s.%s)",
          annotationClass.getSimpleName(), duplicateId, enclosingElement.getQualifiedName(),
          element.getSimpleName());
      hasError = true;
    }
     //获取该注解ListenerClass.class注解,什么意思呢?就是   
     //butterknife提供的方法注解 包含了另外一个注解
     //可以跳过代码看下面的文字说明。
    ListenerClass listener = annotationClass.getAnnotation(ListenerClass.class);
    if (listener == null) {
      throw new IllegalStateException(
          String.format("No @%s defined on @%s.", ListenerClass.class.getSimpleName(),
              annotationClass.getSimpleName()));
    }

//检查id的合法性,里面有个Optional注解
    for (int id : ids) {
       //id 为 -1 ,不合法     
      if (id == NO_ID.value) {
        if (ids.length == 1) {
        //一个参数情况,且方法的参数适用了Optional注解,则抛出异常
          if (!required) {
            error(element, "ID-free binding must not be annotated with @Optional. (%s.%s)",
                enclosingElement.getQualifiedName(), element.getSimpleName());
            hasError = true;
          }
        } else {
          error(element, "@%s annotation contains invalid ID %d. (%s.%s)",
              annotationClass.getSimpleName(), id, enclosingElement.getQualifiedName(),
              element.getSimpleName());
          hasError = true;
        }
      }
    }


     //获取实现的方法
    ListenerMethod method;
    ListenerMethod[] methods = listener.method();

    // methods就是OnItemClick 注解的ListenerClass注解的初始化值,
    比如下面这种,肯定是个
    //    method = @ListenerMethod(
    //   name = "onItemClick",
    //   parameters = {
    //   "android.widget.AdapterView<?>",
    //    "android.view.View",
    //        "int",
    //        "long"
    //    }
    //  )






    if (methods.length > 1) {
    //抛异常,不可能走到这因为butterknife提供的都是1个默认的,能骗到我,我可是上过小学的人,哈哈
      throw new IllegalStateException(String.format("Multiple listener methods specified on @%s.",
          annotationClass.getSimpleName()));
    } else if (methods.length == 1) {

//如果有method属性值即这种onItemClick,则callbacks必须为空,也就是2者不能同时使用

      if (listener.callbacks() != ListenerClass.NONE.class) {
        throw new IllegalStateException(
            String.format("Both method() and callback() defined on @%s.",
                annotationClass.getSimpleName()));
      }
      method = methods[0];
    } else {
    // 否则使用callback
    //反射ListenerClass注解中的callback方法

      Method annotationCallback = annotationClass.getDeclaredMethod("callback");
      Enum<?> callback = (Enum<?>) annotationCallback.invoke(annotation);
      Field callbackField = callback.getDeclaringClass().getField(callback.name());
      method = callbackField.getAnnotation(ListenerMethod.class);

      //如果没有ListenerMethod.class注解 抛出异常,也就是说你使用了callback,则必须提供ListenerMethod.class注解

      if (method == null) {
        throw new IllegalStateException(
            String.format("No @%s defined on @%s's %s.%s.", ListenerMethod.class.getSimpleName(),
                annotationClass.getSimpleName(), callback.getDeclaringClass().getSimpleName(),
                callback.name()));
      }
    }

    //检查方法的合法性,就是你使用的注解的方法的参数不能butterknife的参数的个数(也就是android系统的那种)

    // Verify that the method has equal to or less than the number of parameters as the listener.
    List<? extends VariableElement> methodParameters = executableElement.getParameters();
    if (methodParameters.size() > method.parameters().length) {
      error(element, "@%s methods can have at most %s parameter(s). (%s.%s)",
          annotationClass.getSimpleName(), method.parameters().length,
          enclosingElement.getQualifiedName(), element.getSimpleName());
      hasError = true;
    }

//检查返回值,就是你使用的注解的方法的参数不能butterknife的参数的个数(也就是android系统的那种)

    // Verify method return type matches the listener.
    TypeMirror returnType = executableElement.getReturnType();
    if (returnType instanceof TypeVariable) {
      TypeVariable typeVariable = (TypeVariable) returnType;
      returnType = typeVariable.getUpperBound();
    }
    if (!returnType.toString().equals(method.returnType())) {
      error(element, "@%s methods must have a '%s' return type. (%s.%s)",
          annotationClass.getSimpleName(), method.returnType(),
          enclosingElement.getQualifiedName(), element.getSimpleName());
      hasError = true;
    }

    if (hasError) {
      return;
    }

//下面是方法参数的检查,不做分析了,太细了。记住一点就行了,你写的不和系统的实现方法一样就抛出异常

    Parameter[] parameters = Parameter.NONE;
    if (!methodParameters.isEmpty()) {
      parameters = new Parameter[methodParameters.size()];
      BitSet methodParameterUsed = new BitSet(methodParameters.size());
      String[] parameterTypes = method.parameters();
      for (int i = 0; i < methodParameters.size(); i++) {
        VariableElement methodParameter = methodParameters.get(i);
        TypeMirror methodParameterType = methodParameter.asType();
        if (methodParameterType instanceof TypeVariable) {
          TypeVariable typeVariable = (TypeVariable) methodParameterType;
          methodParameterType = typeVariable.getUpperBound();
        }

        for (int j = 0; j < parameterTypes.length; j++) {
          if (methodParameterUsed.get(j)) {
            continue;
          }
          if (isSubtypeOfType(methodParameterType, parameterTypes[j])
              || isInterface(methodParameterType)) {
            parameters[i] = new Parameter(j, TypeName.get(methodParameterType));
            methodParameterUsed.set(j);
            break;
          }
        }
        if (parameters[i] == null) {
          StringBuilder builder = new StringBuilder();
          builder.append("Unable to match @")
              .append(annotationClass.getSimpleName())
              .append(" method arguments. (")
              .append(enclosingElement.getQualifiedName())
              .append('.')
              .append(element.getSimpleName())
              .append(')');
          for (int j = 0; j < parameters.length; j++) {
            Parameter parameter = parameters[j];
            builder.append("\n\n  Parameter #")
                .append(j + 1)
                .append(": ")
                .append(methodParameters.get(j).asType().toString())
                .append("\n    ");
            if (parameter == null) {
              builder.append("did not match any listener parameters");
            } else {
              builder.append("matched listener parameter #")
                  .append(parameter.getListenerPosition() + 1)
                  .append(": ")
                  .append(parameter.getType());
            }
          }
          builder.append("\n\nMethods may have up to ")
              .append(method.parameters().length)
              .append(" parameter(s):\n");
          for (String parameterType : method.parameters()) {
            builder.append("\n  ").append(parameterType);
          }
          builder.append(
              "\n\nThese may be listed in any order but will be searched for from top to bottom.");
          error(executableElement, builder.toString());
          return;
        }
      }
    }

//最后构造MethodViewBinding实体,形成方法的实体

    MethodViewBinding binding = new MethodViewBinding(name, Arrays.asList(parameters), required);
    //构造BindingClass
    BindingClass bindingClass = getOrCreateTargetClass(targetClassMap, enclosingElement);
    for (int id : ids) {

    //将生成的方法加入到bindingClass的方法集合中,一切都是为了生存java代码而准备。

      if (!bindingClass.addMethod(getId(id), listener, method, binding)) {
        error(element, "Multiple listener methods with return value specified for ID %d. (%s.%s)",
            id, enclosingElement.getQualifiedName(), element.getSimpleName());
        return;
      }
    }

    // Add the type-erased version to the valid binding targets set.
    erasedTargetNames.add(enclosingElement);
  }

ListenerClass/ListenerMethod 注解说明

@Target(METHOD)
@Retention(CLASS)
@ListenerClass(
    targetType = "android.widget.AdapterView<?>",
    setter = "setOnItemClickListener",
    type = "android.widget.AdapterView.OnItemClickListener",
    method = @ListenerMethod(
        name = "onItemClick",
        parameters = {
            "android.widget.AdapterView<?>",
            "android.view.View",
            "int",
            "long"
        }
    )
)
public @interface OnItemClick {
  /** View IDs to which the method will be bound. */
  @IdRes int[] value() default { View.NO_ID };
}
import java.lang.annotation.Retention;
import java.lang.annotation.Target;

import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;

@Retention(RUNTIME) @Target(ANNOTATION_TYPE)
public @interface ListenerClass {
  String targetType();

  /** Name of the setter method on the {@linkplain #targetType() target type} for the listener. */
  String setter();

  /**
   * Name of the method on the {@linkplain #targetType() target type} to remove the listener. If
   * empty {@link #setter()} will be used by default.
   */
  String remover() default "";

  /** Fully-qualified class name of the listener type. */
  String type();

  /** Enum which declares the listener callback methods. Mutually exclusive to {@link #method()}. */
  Class<? extends Enum<?>> callbacks() default NONE.class;

  /**
   * Method data for single-method listener callbacks. Mutually exclusive with {@link #callbacks()}
   * and an error to specify more than one value.
   */
  ListenerMethod[] method() default { };

  /** Default value for {@link #callbacks()}. */
  enum NONE { }
}
package butterknife.internal;

import java.lang.annotation.Retention;
import java.lang.annotation.Target;

import static java.lang.annotation.ElementType.FIELD;
import static java.lang.annotation.RetentionPolicy.RUNTIME;

@Retention(RUNTIME) @Target(FIELD)
public @interface ListenerMethod {
  /** Name of the listener method for which this annotation applies. */
  String name();

  /** List of method parameters. If the type is not a primitive it must be fully-qualified. */
  String[] parameters() default { };

  /** Primitive or fully-qualified return type of the listener method. May also be {@code void}. */
  String returnType() default "void";

  /** If {@link #returnType()} is not {@code void} this value is returned when no binding exists. */
  String defaultReturn() default "null";
}

可以把这3个整体来看。ListenerMethod 这个注解包含了方法的返回值,名字,参数,是实现的那些方法;ListenerClass是set的那些方法属性,包含setter等,我们看到了OnItemClick设置的值就是我们平常写的那种,嘻嘻。

至此,我们的findAndParseTargets方法算是走完了。里面有很多细节。
为什么要分析有关细节呢?可以学习下大神的方法和理解有关处理的细节啊,哈哈。
深入理解ButterKnife源码并掌握原理(三)

作者:ta893115871 发表于2016/9/10 22:20:50 原文链接
阅读:37 评论:0 查看评论

深入理解ButterKnife源码并掌握原理(三)

$
0
0

上两篇我们分析完了处理器的process方法的findAndParseTargets方法来获取了一个集合,该集合包含了你使用注解的类的TypeElement和这个类中的注解的实例BindingClass。
我们再看下处理器的核心方法 process方法

 @Override public boolean process(Set<? extends TypeElement> elements, RoundEnvironment env) {
 //这个方法返回stirng类型的set集合,集合里包含了你需要处理的注解
    Map<TypeElement, BindingClass> targetClassMap = findAndParseTargets(env);

//遍历生存生成java 文件
    for (Map.Entry<TypeElement, BindingClass> entry : targetClassMap.entrySet()) {
      TypeElement typeElement = entry.getKey();
      BindingClass bindingClass = entry.getValue();

      JavaFile javaFile = bindingClass.brewJava();
      try {
        javaFile.writeTo(filer);
      } catch (IOException e) {
        error(typeElement, "Unable to write binding for type %s: %s", typeElement, e.getMessage());
      }
    }

//表示处理器正确处理了
    return true;
  }
  ```
我们先看一下BindingClass的一些成员变量。这里我们主要是看关键的一些集合

  ```
  //这个是BindView 注解在findAndParseTargets 方法解析后 形成ViewBindings实体通过该类的addxx方法添加到viewIdMap集合的对象

  private final Map<Id, ViewBindings> viewIdMap = new LinkedHashMap<>();

     //这个是BindViews 注解 在findAndParseTargets 方法解析后 形成的.
     BindViews用法:

     @BindViews({ R2.id.title, R2.id.subtitle, R2.id.hello }) List<View> headerViews;


     //key:FieldCollectionViewBinding 为实体,包含了名字,类型等信息,大家可以看下源码,这里就不说了就是一个java-bean ,你可以这么理解。
     //value:
     就是这些id: R2.id.title, R2.id.subtitle, R2.id.hello 



  private final Map<FieldCollectionViewBinding, List<Id>> collectionBindings =
      new LinkedHashMap<>();

      //该集合是BindBitmap注解在findAndParseTargets 注解在findAndParseTargets 方法解析后 形成FieldBitmapBinding实体通过该类的addxx方法添加到bitmapBindings集合的对象

  private final List<FieldBitmapBinding> bitmapBindings = new ArrayList<>();
  //这个就是BindDrawable注解....
  private final List<FieldDrawableBinding> drawableBindings = new ArrayList<>();
  //这个就是BindFloat,BindInt,BindString... 这些注解....
  private final List<FieldResourceBinding> resourceBindings = new ArrayList<>();

上面的addxxx方法类似下面的,当然还有其它的就不贴出了

void addFieldCollection(List<Id> ids, FieldCollectionViewBinding binding) {
    collectionBindings.put(binding, ids);
  }

  boolean addMethod(
      Id id,
      ListenerClass listener,
      ListenerMethod method,
      MethodViewBinding binding) {
    ViewBindings viewBindings = getOrCreateViewBindings(id);
    if (viewBindings.hasMethodBinding(listener, method) && !"void".equals(method.returnType())) {
      return false;
    }
    viewBindings.addMethodBinding(listener, method, binding);
    return true;
  }

  void addResource(FieldResourceBinding binding) {
    resourceBindings.add(binding);
  }  

  //......

 ```
至此我们算是完成了一个大步走,我们把所有的注解 方法等放倒了一个集合里,生成java文件的时候就可以遍历这些集合了,从而形成有一定规律的java源文件。
形成的文件就是:
这里我们拿官方的demo-SimpleActivity
编译完后最后生成的文件为:SimpleActivity_ViewBinding
离目标越来越近了。哈哈
### .java文件生成
生成.java文件你可以用字符串拼接的笨方法,但是我们的jake大神怎么可能那么弱。人家自己又写了一个库。javapoet ,66666
compile 'com.squareup:javapoet:1.7.0'
 这个库可以很方便的生成我们想要的java文件。
 在findAndParseTargets方法

 ```
 //...
 //遍历生存生成java 文件
    for (Map.Entry<TypeElement, BindingClass> entry : targetClassMap.entrySet()) {
      TypeElement typeElement = entry.getKey();
      BindingClass bindingClass = entry.getValue();

      JavaFile javaFile = bindingClass.brewJava();
      try {
        javaFile.writeTo(filer);
      } catch (IOException e) {
        error(typeElement, "Unable to write binding for type %s: %s", typeElement, e.getMessage());
      }
    }

遍历targetClassMap集合,调用每一个类的brewJava()方法,最后返回JavaFile对象,再通过writeTo方法生成java文件。
接下来我们就看下bindingClass.brewJava()方法。


//我们可以看到javapoet这个开源库使用了设计模式-builder模式。
// 我们看源码就是看这些模式啦,思想啦,才能提高自己的代码编写能力
//bug少了才有时间干别的呀,哈哈 。。。你懂我的

  JavaFile brewJava() {
  //参数1:包名
   //参数2:TypeSpec,这个可以生成class ,interface 等java文件
    return JavaFile.builder(bindingClassName.packageName(), createBindingClass())
    //注释
        .addFileComment("Generated code from Butter Knife. Do not modify!")
        .build();  }

主要步骤
1. 生成类名
2. 生成构造函数
3. 生成unbind方法。

  private TypeSpec createBindingClass() {

  1. 生成类名
  //bindingClassName.simpleName() 就是我们在findAndParseTargets方法形成的类的名字:xxx_ViewBinding名字
  xxx也就是使用butterknife的类名

    TypeSpec.Builder result = TypeSpec.classBuilder(bindingClassName.simpleName())
    //增加类修饰符public
        .addModifiers(PUBLIC);

 //使用butterknife的类是 final类
    TypeName targetType;
    if (isFinal) {
     //增加类修饰符FINAL
      result.addModifiers(FINAL);
      targetType = targetTypeName;
    } else {
    //不是final类,增加泛型参数T
      targetType = TypeVariableName.get("T");
      result.addTypeVariable(TypeVariableName.get("T", targetTypeName));
    }

//如果有父类直接继承
    if (hasParentBinding()) {
result.superclass(ParameterizedTypeName.get(getParentBinding(), targetType));
    } else {
    //增加实现接口
      result.addSuperinterface(UNBINDER);
       //增加成员变量
      result.addField(targetType, "target", isFinal ? PRIVATE : PROTECTED);
    }

    //到这里生成的代码如下:
    //比如在activity
    public class SimpleActivity_ViewBinding<T extends SimpleActivity> implements Unbinder {
  protected T target;
  }
  //比如在adapter的viewholder中
public final class SimpleAdapter$ViewHolder_ViewBinding implements Unbinder {
  private SimpleAdapter.ViewHolder target;
}


2. 生成构造函数

    if (!bindNeedsView()) {
      // Add a delegating constructor with a target type + view signature for reflective use.
      result.addMethod(createBindingViewDelegateConstructor(targetType));
    }
    result.addMethod(createBindingConstructor(targetType));

  3. 生成unbind方法。
    if (hasViewBindings() || !hasParentBinding()) {
      result.addMethod(createBindingUnbindMethod(result, targetType));
    }

    return result.build();
  }

(一)生成类名

代码里注释的比较详细了

(二)生成构造函数

主要是createBindingConstructor 方法,主要是对成员变量赋值,以及设置监听事件。先看下javapoet提供的几个方法或类:

1.MethodSpec:生成方法的辅助类

这里主要是生成构造函数,当然也可以生成其它的普通方法,构造函数也是方法的一种吗。
通过constructorBuilder构造出一个方法,通过addAnnotation添加注解,通过addModifiers添加修饰符。

  MethodSpec.Builder constructor = 
  MethodSpec.constructorBuilder()
        .addAnnotation(UI_THREAD)
        .addModifiers(PUBLIC);

通过如下方法添加参数targetType为参数类型,”target”为参数的变量名

     constructor.addParameter(targetType, "target");

通过如下方法添加代码语句
第一参数是String类型,可以有占位符ST(类型)等
第二个参数Object… args,类型,多参数不固定。
就像你平时使用String.format()方法一样的意思.

   constructor.addStatement("this.target = target");
2.构造函数中变量的赋值

这里主要是对使用了如下的代码进行一个赋值操作。

  @BindView(R2.id.title) TextView title;
 @OnClick(R2.id.hello) void sayHello() {}

这里我们主要看一下关键方法,因为都是类似的拼接代码字符串。
我们看一下变量的赋值:

  private void addViewBindings(MethodSpec.Builder result, ViewBindings bindings) {
    if (bindings.isSingleFieldBinding()) {
      // Optimize the common case where there's a single binding directly to a field.
      FieldViewBinding fieldBinding = bindings.getFieldBinding();
      CodeBlock.Builder builder = CodeBlock.builder()
          .add("target.$L = ", fieldBinding.getName());

      boolean requiresCast = requiresCast(fieldBinding.getType());
      if (!requiresCast && !fieldBinding.isRequired()) {
        builder.add("source.findViewById($L)", bindings.getId().code);
      } else {
        builder.add("$T.find", UTILS);
        builder.add(fieldBinding.isRequired() ? "RequiredView" : "OptionalView");
        if (requiresCast) {
          builder.add("AsType");
        }
        builder.add("(source, $L", bindings.getId().code);
        if (fieldBinding.isRequired() || requiresCast) {
          builder.add(", $S", asHumanDescription(singletonList(fieldBinding)));
        }
        if (requiresCast) {
          builder.add(", $T.class", fieldBinding.getRawType());
        }
        builder.add(")");
      }
      result.addStatement("$L", builder.build());
      return;
    }

    List<ViewBinding> requiredViewBindings = bindings.getRequiredBindings();
    if (requiredViewBindings.isEmpty()) {
      result.addStatement("view = source.findViewById($L)", bindings.getId().code);
    } else if (!bindings.isBoundToRoot()) {
      result.addStatement("view = $T.findRequiredView(source, $L, $S)", UTILS,
          bindings.getId().code, asHumanDescription(requiredViewBindings));
    }

    addFieldBindings(result, bindings);
    addMethodBindings(result, bindings);
  }

主要是调用系统的findViewById 方法,但是你看到了findRequiredViewAsType,findRequiredView方法和castView方法,findRequiredView,findRequiredViewAsType是作者为乐代码的书写方便对findViewById的一层封装,你可以看一下源码,最后都会调用的findRequiredView方法的findViewById方法。

 public static View findRequiredView(View source, @IdRes int id, String who) {
    View view = source.findViewById(id);
    if (view != null) {
      return view;
    }
    String name = getResourceEntryName(source, id);
    throw new IllegalStateException("Required view '"
        + name
        + "' with ID "
        + id
        + " for "
        + who
        + " was not found. If this view is optional add '@Nullable' (fields) or '@Optional'"
        + " (methods) annotation.");
 }

这个castView是什么方法呢?是Class类的方法,直接转换为指定的类型

   public static <T> T castView(View view, @IdRes int id, String who, Class<T> cls) {
    try {
      return cls.cast(view);
    } catch (ClassCastException e) {
      String name = getResourceEntryName(view, id);
      throw new IllegalStateException("View '"
          + name
          + "' with ID "
          + id
          + " for "
          + who
          + " was of the wrong type. See cause for more info.", e);
    }
  }

说白了都是调用系统的方法。
好了到这里成员变量的赋值算是完了。
注意一点target.title target就是我们的activity或者view ;也验证了为什么是使用了类似BindView注解不能是private修饰符的另一个原因了。

接下来是方法的监听 private void addMethodBindings(MethodSpec.Builder result, ViewBindings bindings) {}方法,李 main 也是通过循环添加方法借助我们上文提到的
MethodSpec.methodBuilder构造器

  for (ListenerMethod method : getListenerMethods(listener)) {
        MethodSpec.Builder callbackMethod = MethodSpec.methodBuilder(method.name())
            .addAnnotation(Override.class)
            .addModifiers(PUBLIC)
            .returns(bestGuess(method.returnType()));
        String[] parameterTypes = method.parameters();
        for (int i = 0, count = parameterTypes.length; i < count; i++) {
          callbackMethod.addParameter(bestGuess(parameterTypes[i]), "p" + i);
          //...
        }

感兴趣的可以根据生成的代码来对照这查看,这里就不多说了。
最后生成的如下所示的代码。

  @UiThread
  public SimpleActivity_ViewBinding(final T target, View source) {
    this.target = target;

    View view;
    target.title = Utils.findRequiredViewAsType(source, R.id.title, "field 'title'", TextView.class);
    target.subtitle = Utils.findRequiredViewAsType(source, R.id.subtitle, "field 'subtitle'", TextView.class);
    view = Utils.findRequiredView(source, R.id.hello, "field 'hello', method 'sayHello', and method 'sayGetOffMe'");
    target.hello = Utils.castView(view, R.id.hello, "field 'hello'", Button.class);
    view2130968578 = view;
    view.setOnClickListener(new DebouncingOnClickListener() {
      @Override
      public void doClick(View p0) {
        target.sayHello();
      }
    });
    view.setOnLongClickListener(new View.OnLongClickListener() {
      @Override
      public boolean onLongClick(View p0) {
        return target.sayGetOffMe();
      }
    });
    view = Utils.findRequiredView(source, R.id.list_of_things, "field 'listOfThings' and method 'onItemClick'");
    target.listOfThings = Utils.castView(view, R.id.list_of_things, "field 'listOfThings'", ListView.class);
    view2130968579 = view;
    ((AdapterView<?>) view).setOnItemClickListener(new AdapterView.OnItemClickListener() {
      @Override
      public void onItemClick(AdapterView<?> p0, View p1, int p2, long p3) {
        target.onItemClick(p2);
      }
    });
    target.footer = Utils.findRequiredViewAsType(source, R.id.footer, "field 'footer'", TextView.class);
    target.headerViews = Utils.listOf(
        Utils.findRequiredView(source, R.id.title, "field 'headerViews'"), 
        Utils.findRequiredView(source, R.id.subtitle, "field 'headerViews'"), 
        Utils.findRequiredView(source, R.id.hello, "field 'headerViews'"));
  }

(三)生成unbind方法

createBindingUnbindMethod方法主要是把的成员变量啦,Listener等 置为空,比如setOnClickListener(null)。

    private MethodSpec createBindingUnbindMethod(TypeSpec.Builder bindingClass,
      TypeName targetType) {
    MethodSpec.Builder result = MethodSpec.methodBuilder("unbind")
        .addAnnotation(Override.class)
        .addModifiers(PUBLIC);
    if (!isFinal && !hasParentBinding()) {
      result.addAnnotation(CALL_SUPER);
    }
    boolean rootBindingWithFields = !hasParentBinding() && hasFieldBindings();
    if (hasFieldBindings() || rootBindingWithFields) {
      result.addStatement("$T target = this.target", targetType);
    }
    if (!hasParentBinding()) {
      String target = rootBindingWithFields ? "target" : "this.target";
      result.addStatement("if ($N == null) throw new $T($S)", target, IllegalStateException.class,
          "Bindings already cleared.");
    } else {
      result.addStatement("super.unbind()");
    }

    if (hasFieldBindings()) {
      result.addCode("\n");
      for (ViewBindings bindings : viewIdMap.values()) {
        if (bindings.getFieldBinding() != null) {
          result.addStatement("target.$L = null", bindings.getFieldBinding().getName());
        }
      }
      for (FieldCollectionViewBinding fieldCollectionBinding : collectionBindings.keySet()) {
        result.addStatement("target.$L = null", fieldCollectionBinding.getName());
      }
    }

    if (hasMethodBindings()) {
      result.addCode("\n");
      for (ViewBindings bindings : viewIdMap.values()) {
        addFieldAndUnbindStatement(bindingClass, result, bindings);
      }
    }

    if (!hasParentBinding()) {
      result.addCode("\n");
      result.addStatement("this.target = null");
    }

    return result.build();
  }

主要就是addStatement方法,上文已经说了,该方法的意思就是生成一句代码,
第一参数是String类型,可以有占位符ST(类型)等
第二个参数Object… args,类型,多参数不固定。
就像你平时使用String.format()方法一样的意思.
比较简单,最后生成的方法类似:

  @Override
  public void unbind() {
    SimpleAdapter.ViewHolder target = this.target;
    if (target == null) throw new IllegalStateException("Bindings already cleared.");

    target.word = null;
    target.length = null;
    target.position = null;

    this.target = null;
  }

深入理解ButterKnife源码并掌握原理(四)

作者:ta893115871 发表于2016/9/10 22:26:46 原文链接
阅读:44 评论:0 查看评论

接口定义语言AIDL实现进程间的通信

$
0
0

在Android中,如果我们需要在不同进程间实现通信,就需要用到AIDL技术去完成。

AIDL(Android Interface Definition Language)是一种接口定义语言,编译器通过*.aidl文件的描述信息生成符合通信协议的Java代码,我们无需自己去写这段繁杂的代码,只需要在需要的时候调用即可,通过这种方式我们就可以完成进程间的通信工作。关于AIDL的编写规则我在这里就不多介绍了,读者可以到网上查找一下相关资料。

接下来,我就演示一个操作AIDL的最基本的流程。

首先,我们需要建立一个服务端的工程,如图所以:


在IPerson.aidl中我们定义了一个“问候”的方法,代码如下:

package com.scott.aidl;  
interface IPerson {  
    String greet(String someone);  
}  
在Eclipse插件的帮助下,编译器会自动在gen目录中生成对应的IPerson.java文件,格式化后的代码如下:
package com.scott.aidl;  
  
public interface IPerson extends android.os.IInterface {  
    /** Local-side IPC implementation stub class. */  
    public static abstract class Stub extends android.os.Binder implements com.scott.aidl.IPerson {  
  
        private static final java.lang.String DESCRIPTOR = "com.scott.aidl.IPerson";  
  
        /** Construct the stub at attach it to the interface. */  
        public Stub() {  
            this.attachInterface(this, DESCRIPTOR);  
        }  
  
        /** 
         * Cast an IBinder object into an com.scott.aidl.IPerson interface, 
         * generating a proxy if needed. 
         */  
        public static com.scott.aidl.IPerson asInterface(android.os.IBinder obj) {  
            if ((obj == null)) {  
                return null;  
            }  
            android.os.IInterface iin = (android.os.IInterface) obj.queryLocalInterface(DESCRIPTOR);  
            if (((iin != null) && (iin instanceof com.scott.aidl.IPerson))) {  
                return ((com.scott.aidl.IPerson) iin);  
            }  
            return new com.scott.aidl.IPerson.Stub.Proxy(obj);  
        }  
  
        public android.os.IBinder asBinder() {  
            return this;  
        }  
  
        @Override  
        public boolean onTransact(int code, android.os.Parcel data, android.os.Parcel reply, int flags)  
                throws android.os.RemoteException {  
            switch (code) {  
                case INTERFACE_TRANSACTION: {  
                    reply.writeString(DESCRIPTOR);  
                    return true;  
                }  
                case TRANSACTION_greet: {  
                    data.enforceInterface(DESCRIPTOR);  
                    java.lang.String _arg0;  
                    _arg0 = data.readString();  
                    java.lang.String _result = this.greet(_arg0);  
                    reply.writeNoException();  
                    reply.writeString(_result);  
                    return true;  
                }  
            }  
            return super.onTransact(code, data, reply, flags);  
        }  
  
        private static class Proxy implements com.scott.aidl.IPerson {  
            private android.os.IBinder mRemote;  
  
            Proxy(android.os.IBinder remote) {  
                mRemote = remote;  
            }  
  
            public android.os.IBinder asBinder() {  
                return mRemote;  
            }  
  
            public java.lang.String getInterfaceDescriptor() {  
                return DESCRIPTOR;  
            }  
  
            public java.lang.String greet(java.lang.String someone) throws android.os.RemoteException {  
                android.os.Parcel _data = android.os.Parcel.obtain();  
                android.os.Parcel _reply = android.os.Parcel.obtain();  
                java.lang.String _result;  
                try {  
                    _data.writeInterfaceToken(DESCRIPTOR);  
                    _data.writeString(someone);  
                    mRemote.transact(Stub.TRANSACTION_greet, _data, _reply, 0);  
                    _reply.readException();  
                    _result = _reply.readString();  
                } finally {  
                    _reply.recycle();  
                    _data.recycle();  
                }  
                return _result;  
            }  
        }  
  
        static final int TRANSACTION_greet = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);  
    }  
  
    public java.lang.String greet(java.lang.String someone) throws android.os.RemoteException;  
}  

IPerson接口中的抽象内部类Stub继承android.os.Binder类并实现IPerson接口,比较重要的方法是asInterface(IBinder)方法,该方法会将IBinder类型的对象转换成IPerson类型,必要的时候生成一个代理对象返回结果。

接下来就是我们的Service了:

package com.scott.server;  
  
import android.app.Service;  
import android.content.Intent;  
import android.os.IBinder;  
import android.os.RemoteException;  
import android.util.Log;  
  
import com.scott.aidl.IPerson;  
  
public class AIDLService extends Service {  
  
    private static final String TAG = "AIDLService";  
  
    IPerson.Stub stub = new IPerson.Stub() {  
        @Override  
        public String greet(String someone) throws RemoteException {  
            Log.i(TAG, "greet() called");  
            return "hello, " + someone;  
        }  
    };  
  
    @Override  
    public IBinder onBind(Intent intent) {  
        Log.i(TAG, "onBind() called");  
        return stub;  
    }  
  
    @Override  
    public boolean onUnbind(Intent intent) {  
        Log.i(TAG, "onUnbind() called");  
        return true;  
    }  
  
    @Override  
    public void onDestroy() {  
        super.onDestroy();  
        Log.i(TAG, "onDestroy() called");  
    }  
}  
我们实现了IPerson.Stub这个抽象类的greet方法,然后再onBind(Intent)方法中返回我们的stub实例,这样一来调用方获取的IPerson.Stub就是我们的这个实例,greet方法也会按照我们的期望那样执行。

当然,要想让Service生效,我们还需要在AndroidManifest.xml中做一些配置工作:

<service android:name=".AIDLService">  
    <intent-filter>  
        <action android:name="android.intent.action.AIDLService" />  
        <category android:name="android.intent.category.DEFAULT" />  
    </intent-filter>  
</service>  
服务端已经完成了,接下来我们就该完成客户端的工作了。我已经建好了一个客户端工程,如图:


我们只需要把IPerson.aidl文件拷到相应的目录中即可,编译器同样会生成相对应的IPerson.java文件,这一部分和服务端没什么区别。这样一来,服务端和客户端就在通信协议上达到了统一。我们主要工作在MainActivity中完成。

MainActivity代码如下:

package com.scott.client;  
  
import android.app.Activity;  
import android.content.ComponentName;  
import android.content.Context;  
import android.content.Intent;  
import android.content.ServiceConnection;  
import android.os.Bundle;  
import android.os.IBinder;  
import android.os.RemoteException;  
import android.util.Log;  
import android.view.View;  
import android.widget.Button;  
import android.widget.Toast;  
  
import com.scott.aidl.IPerson;  
  
public class MainActivity extends Activity {  
  
    private Button bindBtn;  
    private Button greetBtn;  
    private Button unbindBtn;  
  
    private IPerson person;  
    private ServiceConnection conn = new ServiceConnection() {  
  
        @Override  
        public void onServiceConnected(ComponentName name, IBinder service) {  
            Log.i("ServiceConnection", "onServiceConnected() called");  
            person = IPerson.Stub.asInterface(service);  
        }  
  
        @Override  
        public void onServiceDisconnected(ComponentName name) {  
            //This is called when the connection with the service has been unexpectedly disconnected,  
            //that is, its process crashed. Because it is running in our same process, we should never see this happen.  
            Log.i("ServiceConnection", "onServiceDisconnected() called");  
        }  
    };  
  
    @Override  
    public void onCreate(Bundle savedInstanceState) {  
        super.onCreate(savedInstanceState);  
        setContentView(R.layout.main);  
  
        bindBtn = (Button) findViewById(R.id.bindBtn);  
        bindBtn.setOnClickListener(new View.OnClickListener() {  
            @Override  
            public void onClick(View v) {  
                Intent intent = new Intent("android.intent.action.AIDLService");  
                bindService(intent, conn, Context.BIND_AUTO_CREATE);  
  
                bindBtn.setEnabled(false);  
                greetBtn.setEnabled(true);  
                unbindBtn.setEnabled(true);  
            }  
        });  
  
        greetBtn = (Button) findViewById(R.id.greetBtn);  
        greetBtn.setOnClickListener(new View.OnClickListener() {  
            @Override  
            public void onClick(View v) {  
                try {  
                    String retVal = person.greet("scott");  
                    Toast.makeText(MainActivity.this, retVal, Toast.LENGTH_SHORT).show();  
                } catch (RemoteException e) {  
                    Toast.makeText(MainActivity.this, "error", Toast.LENGTH_SHORT).show();  
                }  
            }  
        });  
  
        unbindBtn = (Button) findViewById(R.id.unbindBtn);  
        unbindBtn.setOnClickListener(new View.OnClickListener() {  
            @Override  
            public void onClick(View v) {  
                unbindService(conn);  
  
                bindBtn.setEnabled(true);  
                greetBtn.setEnabled(false);  
                unbindBtn.setEnabled(false);  
            }  
        });  
    }  
}  
从代码中可以看到,我们要重写ServiceConnection中的onServiceConnected方法将IBinder类型的对像转换成我们的IPerson类型。到现在我们就剩下最后一个步骤了,这个环节也是最为关键的,就是绑定我们需要的服务。我们通过服务端Service定义的“android.intent.action.AIDLService”这个标识符来绑定其服务,这样客户端和服务端就实现了通信的连接,我们就可以调用IPerson中的“问候”方法了。

最后,贴几张客户端演示过程图。


 按照顺序分别是:初始界面;点击bindService后界面;点击greet后界面;点击unbindService后界面。

操作过程中的日志如下:





作者:bryant_liu24 发表于2016/9/10 22:47:00 原文链接
阅读:62 评论:0 查看评论

Android简易实战教程--第二十九话《创建图片副本》

$
0
0

承接第二十八话加载大图片,本篇介绍如何创建一个图片的副本。

安卓中加载的原图是无法对其修改的,因为默认权限是只读的。但是通过创建副本,就可以对其做一些修改,绘制等了。

首先创建一个简单的布局。一个放原图,一个放副本copy

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity" 
    android:orientation="vertical"
    >

    <ImageView
        android:id="@+id/iv_src"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        />
    <ImageView
        android:id="@+id/iv_copy"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        />

</LinearLayout>

总共十几行代码,但是还是比较难理解;详细的注释写在里面了:

package com.itandroid.copy;

import android.os.Bundle;
import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.view.Menu;
import android.widget.ImageView;

public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        //这个对象是只读的Decode a file path into a bitmap.没法做修改
        Bitmap bmSrc = BitmapFactory.decodeFile("sdcard/photo3.jpg");
        
        //创建图片副本,才可以对图片修改
        //1.在内存中创建一个与原图一模一样大小的bitmap对象,创建与原图大小一致的白纸。此时没有内容,因为没有绘制,但是这时的Bitmap对象是可读可写的,即可以对其修改
        Bitmap bmCopy = Bitmap.createBitmap(bmSrc.getWidth(), bmSrc.getHeight(), bmSrc.getConfig());//第三个参数表示一些配置信息,设置与原来图片一样
        
        /**  对该位图对象进行绘制    **/
        //2.创建画笔对象
        Paint paint = new Paint();
        
        //3.创建画板对象,把白纸(副本Bitmap)铺在画板上(这里放原图是不可以的)
        Canvas canvas = new Canvas(bmCopy);
        
        //4.开始作画,把原图的内容绘制在白纸上;此时副本就有了与原图一模一样的内容
        canvas.drawBitmap(bmSrc, new Matrix(), paint);//第二个参数是一个矩阵
        
        ImageView iv_src = (ImageView) findViewById(R.id.iv_src);
        ImageView iv_copy = (ImageView) findViewById(R.id.iv_copy);
        iv_src.setImageBitmap(bmSrc);
        iv_copy.setImageBitmap(bmCopy);
    }

}

看看运行结果,创建了一个一模一样的图片。

但是,新创建的图片是可以做一些“”特效”的,下一话将介绍图片的特效处理:


欢迎关注本博客点击打开链接  http://blog.csdn.net/qq_32059827,每天花上5分钟,阅读一篇有趣的安卓小文哦

作者:qq_32059827 发表于2016/9/10 22:58:15 原文链接
阅读:77 评论:0 查看评论

探究underscore v1.8.3版本源码

$
0
0

一直想学习一下类库的源码, jQuery 刚刚看到选择器那块,直接被那一大块正则搞懵逼了。经过同事的推荐,选择了 underscore 来作为类库研究的起点。

闭包

所有函数都在一个闭包内,避免污染全局变量,这没什么特殊的,略过。。。

(function() { ...    
}());

全局对象的获取

先看下面一段代码:

var root = typeof self == 'object' && self.self === self && self ||
           typeof global == 'object' && global.global === global && global ||
           this;

self 是什么鬼? global 跟 this 都能够猜出来是全局变量,这个 self 从哪里冒出来的?

第一眼看到这样的代码很困惑,感觉压根没有头绪。但是如果你打开 chrome 的控制台,神奇的事情发生了

其实查看源码的注释,我们也能看出来这段代码的作用:在不一样的环境里面获取当前全局对象 this

self | window
global
this

为了压缩所做的原型赋值

源码中有将对象的原型链赋值给一个变量的做法:

var ArrayProto = Array.prototype, ObjProto = Object.prototype;
var SymbolProto = typeof Symbol !== 'undefined' ? Symbol.prototype : null;

一开始我并没明白这么做的优势,代码不都一样吗?

参考注释并且上网查资料才知道原因:为了压缩

举个例子, Array.prototype 是没有办法经过压缩的, Array , prototype 这些,如果改了,浏览器就无法识别这些字段了。

但经过类似上面代码的处理, ObjProto 经过压缩就能变成变量 a ,那么原来的代码就会变成 a.xxx 。

我们平常写的代码也可以进行类似上面的处理,只要代码的复用超过两次,就可以考虑将其赋值给一个变量了。

this 值统一处理

this 在类库中的应用很广泛, undersocre 采用了一个内部函数来处理 this

var optimizeCb = function(func, context, argCount) {
    if (context === void 0) return func;
    switch (argCount == null ? 3 : argCount) {
      case 1: return function(value) {
        return func.call(context, value);
      };
      // The 2-parameter case has been omitted only because no current consumers
      // made use of it.
      case 3: return function(value, index, collection) {
        return func.call(context, value, index, collection);
      };
      case 4: return function(accumulator, value, index, collection) {
        return func.call(context, accumulator, value, index, collection);
      };
    }
    return function() {
      return func.apply(context, arguments);
    };
  };

注意到上面的 case 语句没有 2 的情况,看其注释基本就能明白,这是因为没有使用到 2 的情况。

上面函数的最后一个参数 argCount 是用来指定参数个数:

  1. 接受单值的情况

  2. 已取消

  3. 迭代器函数

  4. reduce 函数

callback 的统一处理

var cb = function(value, context, argCount) {
    if (_.iteratee !== builtinIteratee) return _.iteratee(value, context);
    if (value == null) return _.identity;
    if (_.isFunction(value)) return optimizeCb(value, context, argCount);
    if (_.isObject(value)) return _.matcher(value);
    return _.property(value);
  };

cb 就是 callback 的简写,看函数的注释的意思是:内部函数,用来生成可应用于集合内每个元素的回调函数,返回预期的结果,具体应用向下看。

iteratee 什么鬼?

_.iteratee = builtinIteratee = function(value, context) {
    return cb(value, context, Infinity);
  };

结合上面的 cb 函数,貌似可以看到每次调用 cb 函数时都会判断一次 _.iteratee 是否等于 builtinIteratee 。

如果不等于则调用 _.iteratee 函数,让 _.iteratee = builtinIteratee,再继续执行 cb 函数。

结合注释,猜测这个函数的作用应该是防止用户自己定义 iteratee 函数。

restArgs 又一个基础函数

var restArgs = function(func, startIndex) {
    startIndex = startIndex == null ? func.length - 1 : +startIndex;
    return function() {
      var length = Math.max(arguments.length - startIndex, 0),
          rest = Array(length),
          index = 0;
      for (; index < length; index++) {
        rest[index] = arguments[index + startIndex];
      }
      switch (startIndex) {
        case 0: return func.call(this, rest);
        case 1: return func.call(this, arguments[0], rest);
        case 2: return func.call(this, arguments[0], arguments[1], rest);
      }
      var args = Array(startIndex + 1);
      for (index = 0; index < startIndex; index++) {
        args[index] = arguments[index];
      }
      args[startIndex] = rest;
      return func.apply(this, args);
    };
  };
http://www.yqcq.gov.cn/e/space/?userid=156706&yqcq.xml?feed_filter=20160910Na9Rt.html
http://www.yqcq.gov.cn/e/space/?userid=156707&yqcq.xml?feed_filter=20160910Oh7Et.html
http://www.yqcq.gov.cn/e/space/?userid=156708&yqcq.xml?feed_filter=20160910Vn6Bg.html
http://www.yqcq.gov.cn/e/space/?userid=156709&yqcq.xml?feed_filter=20160910Tf0Hc.html
http://www.yqcq.gov.cn/e/space/?userid=156710&yqcq.xml?feed_filter=20160910Ka0Im.html
http://www.yqcq.gov.cn/e/space/?userid=156712&yqcq.xml?feed_filter=20160910Lr4Nb.html
http://www.yqcq.gov.cn/e/space/?userid=156713&yqcq.xml?feed_filter=20160910Jt2Jh.html
http://www.yqcq.gov.cn/e/space/?userid=156715&yqcq.xml?feed_filter=20160910Jj7Ra.html
http://www.yqcq.gov.cn/e/space/?userid=156716&yqcq.xml?feed_filter=20160910Oz2Uz.html
http://www.yqcq.gov.cn/e/space/?userid=156717&yqcq.xml?feed_filter=20160910Ue2Mq.html
http://www.yqcq.gov.cn/e/space/?userid=156719&yqcq.xml?feed_filter=20160910Eb6En.html
http://www.yqcq.gov.cn/e/space/?userid=156720&yqcq.xml?feed_filter=20160910Dq9Lx.html
http://www.yqcq.gov.cn/e/space/?userid=156721&yqcq.xml?feed_filter=20160910Sj3Ym.html
http://www.yqcq.gov.cn/e/space/?userid=156722&yqcq.xml?feed_filter=20160910Qh8My.html
http://www.yqcq.gov.cn/e/space/?userid=156724&yqcq.xml?feed_filter=20160910If2Ud.html
http://www.yqcq.gov.cn/e/space/?userid=156725&yqcq.xml?feed_filter=20160910Ta4Ua.html
http://www.yqcq.gov.cn/e/space/?userid=156726&yqcq.xml?feed_filter=20160910Ha3Du.html
http://www.yqcq.gov.cn/e/space/?userid=156728&yqcq.xml?feed_filter=20160910Dv7Sq.html
http://www.yqcq.gov.cn/e/space/?userid=156729&yqcq.xml?feed_filter=20160910Un6Nt.html
http://www.yqcq.gov.cn/e/space/?userid=156730&yqcq.xml?feed_filter=20160910Pf1Ha.html
http://www.yqcq.gov.cn/e/space/?userid=156731&yqcq.xml?feed_filter=20160910Rw0Nc.html
http://www.yqcq.gov.cn/e/space/?userid=156732&yqcq.xml?feed_filter=20160910Ko7Yk.html
http://www.yqcq.gov.cn/e/space/?userid=156733&yqcq.xml?feed_filter=20160910Wc9Th.html
http://www.yqcq.gov.cn/e/space/?userid=156734&yqcq.xml?feed_filter=20160910Kh9Cm.html
http://www.yqcq.gov.cn/e/space/?userid=156735&yqcq.xml?feed_filter=20160910Qn9Ew.html
http://www.yqcq.gov.cn/e/space/?userid=156737&yqcq.xml?feed_filter=20160910Fi9Aa.html
http://www.yqcq.gov.cn/e/space/?userid=156738&yqcq.xml?feed_filter=20160910Ov4Fb.html
http://www.yqcq.gov.cn/e/space/?userid=156739&yqcq.xml?feed_filter=20160910Db2Yk.html
http://www.yqcq.gov.cn/e/space/?userid=156741&yqcq.xml?feed_filter=20160910Xq3Hy.html
http://www.yqcq.gov.cn/e/space/?userid=156742&yqcq.xml?feed_filter=20160910Ai4Ln.html
http://www.yqcq.gov.cn/e/space/?userid=156743&yqcq.xml?feed_filter=20160910Yw1Fn.html
http://www.yqcq.gov.cn/e/space/?userid=156745&yqcq.xml?feed_filter=20160910Fm6Rp.html
http://www.yqcq.gov.cn/e/space/?userid=156746&yqcq.xml?feed_filter=20160910Hw7Oy.html
http://www.yqcq.gov.cn/e/space/?userid=156747&yqcq.xml?feed_filter=20160910Qb4Mr.html
http://www.yqcq.gov.cn/e/space/?userid=156748&yqcq.xml?feed_filter=20160910Rc2Xo.html
http://www.yqcq.gov.cn/e/space/?userid=156750&yqcq.xml?feed_filter=20160910Mg2Gr.html
http://www.yqcq.gov.cn/e/space/?userid=156751&yqcq.xml?feed_filter=20160910Fo0Ii.html
http://www.yqcq.gov.cn/e/space/?userid=156752&yqcq.xml?feed_filter=20160910Lh3Ce.html
http://www.yqcq.gov.cn/e/space/?userid=156753&yqcq.xml?feed_filter=20160910Rs4Ej.html
http://www.yqcq.gov.cn/e/space/?userid=156754&yqcq.xml?feed_filter=20160910Xo9Oi.html
http://www.yqcq.gov.cn/e/space/?userid=156756&yqcq.xml?feed_filter=20160910Jk9Hl.html
http://www.yqcq.gov.cn/e/space/?userid=156758&yqcq.xml?feed_filter=20160910Or4Uq.html
http://www.yqcq.gov.cn/e/space/?userid=156759&yqcq.xml?feed_filter=20160910Jf7Sp.html
http://www.yqcq.gov.cn/e/space/?userid=156760&yqcq.xml?feed_filter=20160910Ig5Cr.html
http://www.yqcq.gov.cn/e/space/?userid=156761&yqcq.xml?feed_filter=20160910Ne2Qi.html
http://www.yqcq.gov.cn/e/space/?userid=156762&yqcq.xml?feed_filter=20160910Fd1Wm.html
http://www.yqcq.gov.cn/e/space/?userid=156763&yqcq.xml?feed_filter=20160910Vn5Tf.html
http://www.yqcq.gov.cn/e/space/?userid=156764&yqcq.xml?feed_filter=20160910Lr3Mm.html
http://www.yqcq.gov.cn/e/space/?userid=156765&yqcq.xml?feed_filter=20160910Va6Ap.html
http://www.yqcq.gov.cn/e/space/?userid=156767&yqcq.xml?feed_filter=20160910Oz8Kt.html
http://www.yqcq.gov.cn/e/space/?userid=156768&yqcq.xml?feed_filter=20160910Uc4Uc.html
http://www.yqcq.gov.cn/e/space/?userid=156769&yqcq.xml?feed_filter=20160910Lh0Oi.html
http://www.yqcq.gov.cn/e/space/?userid=156771&yqcq.xml?feed_filter=20160910Sl8Rj.html
http://www.yqcq.gov.cn/e/space/?userid=156772&yqcq.xml?feed_filter=20160910Mf7Od.html
http://www.yqcq.gov.cn/e/space/?userid=156773&yqcq.xml?feed_filter=20160910Hp5Kw.html
http://www.yqcq.gov.cn/e/space/?userid=156774&yqcq.xml?feed_filter=20160910Pu4Zv.html
http://www.yqcq.gov.cn/e/space/?userid=156775&yqcq.xml?feed_filter=20160910Bd4Yf.html
http://www.yqcq.gov.cn/e/space/?userid=156776&yqcq.xml?feed_filter=20160910Kw3Ua.html
http://www.yqcq.gov.cn/e/space/?userid=156778&yqcq.xml?feed_filter=20160910Yd9Jm.html
http://www.yqcq.gov.cn/e/space/?userid=156779&yqcq.xml?feed_filter=20160910Tj9Gz.html
http://www.yqcq.gov.cn/e/space/?userid=156780&yqcq.xml?feed_filter=20160910Wr5Hf.html
http://www.yqcq.gov.cn/e/space/?userid=156781&yqcq.xml?feed_filter=20160910Gp9Hn.html
http://www.yqcq.gov.cn/e/space/?userid=156782&yqcq.xml?feed_filter=20160910Pi4Pu.html
http://www.yqcq.gov.cn/e/space/?userid=156783&yqcq.xml?feed_filter=20160910Ph1Pm.html
http://www.yqcq.gov.cn/e/space/?userid=156785&yqcq.xml?feed_filter=20160910Rk3Ez.html
http://www.yqcq.gov.cn/e/space/?userid=156786&yqcq.xml?feed_filter=20160910Ts9Dz.html
http://www.yqcq.gov.cn/e/space/?userid=156787&yqcq.xml?feed_filter=20160910Fy0Xc.html
http://www.yqcq.gov.cn/e/space/?userid=156788&yqcq.xml?feed_filter=20160910Ic6Ym.html
http://www.yqcq.gov.cn/e/space/?userid=156789&yqcq.xml?feed_filter=20160910Xw8Sq.html
http://www.yqcq.gov.cn/e/space/?userid=157022&yqcq.xml?feed_filter=20160910Ve4Sg.html
http://www.yqcq.gov.cn/e/space/?userid=157023&yqcq.xml?feed_filter=20160910Tc9Tc.html
http://www.yqcq.gov.cn/e/space/?userid=157024&yqcq.xml?feed_filter=20160910Pu5Mv.html
http://www.yqcq.gov.cn/e/space/?userid=157025&yqcq.xml?feed_filter=20160910Oo4Fi.html
http://www.yqcq.gov.cn/e/space/?userid=157026&yqcq.xml?feed_filter=20160910Ct9Nv.html
http://www.yqcq.gov.cn/e/space/?userid=157027&yqcq.xml?feed_filter=20160910Kr0Zc.html
http://www.yqcq.gov.cn/e/space/?userid=157028&yqcq.xml?feed_filter=20160910Dp9Ao.html
http://www.yqcq.gov.cn/e/space/?userid=157029&yqcq.xml?feed_filter=20160910Ka1Tt.html
http://www.yqcq.gov.cn/e/space/?userid=157030&yqcq.xml?feed_filter=20160910Oe4Fv.html
http://www.yqcq.gov.cn/e/space/?userid=157031&yqcq.xml?feed_filter=20160910Uk9Pd.html
http://www.yqcq.gov.cn/e/space/?userid=157032&yqcq.xml?feed_filter=20160910Fi9Zx.html
http://www.yqcq.gov.cn/e/space/?userid=157033&yqcq.xml?feed_filter=20160910Sg9Gb.html
http://www.yqcq.gov.cn/e/space/?userid=157034&yqcq.xml?feed_filter=20160910Bn4Jo.html
http://www.yqcq.gov.cn/e/space/?userid=157035&yqcq.xml?feed_filter=20160910Lc5Oi.html
http://www.yqcq.gov.cn/e/space/?userid=157036&yqcq.xml?feed_filter=20160910Xw1An.html
http://www.yqcq.gov.cn/e/space/?userid=157037&yqcq.xml?feed_filter=20160910Xh5Ui.html
http://www.yqcq.gov.cn/e/space/?userid=157038&yqcq.xml?feed_filter=20160910Rr4Jn.html
http://www.yqcq.gov.cn/e/space/?userid=157039&yqcq.xml?feed_filter=20160910Wp2Wk.html
http://www.yqcq.gov.cn/e/space/?userid=157040&yqcq.xml?feed_filter=20160910Yb5Xg.html
http://www.yqcq.gov.cn/e/space/?userid=157041&yqcq.xml?feed_filter=20160910Ai3Df.html
http://www.yqcq.gov.cn/e/space/?userid=157042&yqcq.xml?feed_filter=20160910Pj9Dh.html
http://www.yqcq.gov.cn/e/space/?userid=157043&yqcq.xml?feed_filter=20160910Gm2Ib.html
http://www.yqcq.gov.cn/e/space/?userid=157044&yqcq.xml?feed_filter=20160910Gn6Rx.html
http://www.yqcq.gov.cn/e/space/?userid=157045&yqcq.xml?feed_filter=20160910Vj7Mt.html
http://www.yqcq.gov.cn/e/space/?userid=157046&yqcq.xml?feed_filter=20160910Wv6Ci.html
http://www.yqcq.gov.cn/e/space/?userid=157047&yqcq.xml?feed_filter=20160910Af6Me.html
http://www.yqcq.gov.cn/e/space/?userid=157048&yqcq.xml?feed_filter=20160910Id9Dh.html
http://www.yqcq.gov.cn/e/space/?userid=157049&yqcq.xml?feed_filter=20160910Tg3Ve.html
http://www.yqcq.gov.cn/e/space/?userid=157050&yqcq.xml?feed_filter=20160910Ql0Lz.html
http://www.yqcq.gov.cn/e/space/?userid=157052&yqcq.xml?feed_filter=20160910Ai6Us.html
http://www.yqcq.gov.cn/e/space/?userid=157053&yqcq.xml?feed_filter=20160910Lm4Xu.html
http://www.yqcq.gov.cn/e/space/?userid=157054&yqcq.xml?feed_filter=20160910Ur5Bg.html
http://www.yqcq.gov.cn/e/space/?userid=157055&yqcq.xml?feed_filter=20160910Au7Gq.html
http://www.yqcq.gov.cn/e/space/?userid=157056&yqcq.xml?feed_filter=20160910Ks5Pn.html
http://www.yqcq.gov.cn/e/space/?userid=157057&yqcq.xml?feed_filter=20160910Jc5Dy.html
http://www.yqcq.gov.cn/e/space/?userid=157058&yqcq.xml?feed_filter=20160910Un5Fg.html
http://www.yqcq.gov.cn/e/space/?userid=157059&yqcq.xml?feed_filter=20160910Vo4Lz.html
http://www.yqcq.gov.cn/e/space/?userid=157060&yqcq.xml?feed_filter=20160910Jo4Qx.html
http://www.yqcq.gov.cn/e/space/?userid=157061&yqcq.xml?feed_filter=20160910Sf8Ve.html
http://www.yqcq.gov.cn/e/space/?userid=157062&yqcq.xml?feed_filter=20160910Cd2Tp.html
http://www.yqcq.gov.cn/e/space/?userid=157063&yqcq.xml?feed_filter=20160910Lb6Tl.html
http://www.yqcq.gov.cn/e/space/?userid=157064&yqcq.xml?feed_filter=20160910Rq5Dk.html
http://www.yqcq.gov.cn/e/space/?userid=157065&yqcq.xml?feed_filter=20160910Zd1Wr.html
http://www.yqcq.gov.cn/e/space/?userid=157066&yqcq.xml?feed_filter=20160910Vr6Tn.html
http://www.yqcq.gov.cn/e/space/?userid=157067&yqcq.xml?feed_filter=20160910Kz5Jj.html
http://www.yqcq.gov.cn/e/space/?userid=157068&yqcq.xml?feed_filter=20160910Po0Gj.html
http://www.yqcq.gov.cn/e/space/?userid=157069&yqcq.xml?feed_filter=20160910By2Dl.html
http://www.yqcq.gov.cn/e/space/?userid=157070&yqcq.xml?feed_filter=20160910Rw4Bu.html
http://www.yqcq.gov.cn/e/space/?userid=157071&yqcq.xml?feed_filter=20160910Sw3Te.html
http://www.yqcq.gov.cn/e/space/?userid=157072&yqcq.xml?feed_filter=20160910Mv2Qx.html
http://www.yqcq.gov.cn/e/space/?userid=157073&yqcq.xml?feed_filter=20160910Ci2Mk.html
http://www.yqcq.gov.cn/e/space/?userid=157074&yqcq.xml?feed_filter=20160910Kx8Kz.html
http://www.yqcq.gov.cn/e/space/?userid=157075&yqcq.xml?feed_filter=20160910Yu1Tm.html
http://www.yqcq.gov.cn/e/space/?userid=157076&yqcq.xml?feed_filter=20160910Yy4Ic.html
http://www.yqcq.gov.cn/e/space/?userid=157077&yqcq.xml?feed_filter=20160910Au5Yo.html
http://www.yqcq.gov.cn/e/space/?userid=157078&yqcq.xml?feed_filter=20160910Lc8Pf.html
http://www.yqcq.gov.cn/e/space/?userid=157079&yqcq.xml?feed_filter=20160910Di8Et.html
http://www.yqcq.gov.cn/e/space/?userid=157080&yqcq.xml?feed_filter=20160910Bt3Yt.html
http://www.yqcq.gov.cn/e/space/?userid=157081&yqcq.xml?feed_filter=20160910Ig3Pw.html
http://www.yqcq.gov.cn/e/space/?userid=157082&yqcq.xml?feed_filter=20160910Fz2Bi.html
http://www.yqcq.gov.cn/e/space/?userid=157083&yqcq.xml?feed_filter=20160910Lx6Nz.html
http://www.yqcq.gov.cn/e/space/?userid=157084&yqcq.xml?feed_filter=20160910Jm6Zv.html
http://www.yqcq.gov.cn/e/space/?userid=157085&yqcq.xml?feed_filter=20160910Ho1Dh.html
http://www.yqcq.gov.cn/e/space/?userid=157086&yqcq.xml?feed_filter=20160910Ag0Om.html
http://www.yqcq.gov.cn/e/space/?userid=157087&yqcq.xml?feed_filter=20160910Zz3Oh.html
http://www.yqcq.gov.cn/e/space/?userid=157088&yqcq.xml?feed_filter=20160910Ry2Zo.html
http://www.yqcq.gov.cn/e/space/?userid=157089&yqcq.xml?feed_filter=20160910Zb0Ku.html
http://www.yqcq.gov.cn/e/space/?userid=157090&yqcq.xml?feed_filter=20160910Lu0Wy.html
http://www.yqcq.gov.cn/e/space/?userid=157091&yqcq.xml?feed_filter=20160910Vs5Vy.html
http://www.yqcq.gov.cn/e/space/?userid=157092&yqcq.xml?feed_filter=20160910Es6Uo.html
http://www.yqcq.gov.cn/e/space/?userid=157093&yqcq.xml?feed_filter=20160910Sw6Iz.html
http://www.yqcq.gov.cn/e/space/?userid=157094&yqcq.xml?feed_filter=20160910Sg3Ub.html
http://www.yqcq.gov.cn/e/space/?userid=157095&yqcq.xml?feed_filter=20160910Dz7Lk.html
http://www.yqcq.gov.cn/e/space/?userid=157096&yqcq.xml?feed_filter=20160910Zg6Hr.html
http://www.yqcq.gov.cn/e/space/?userid=157097&yqcq.xml?feed_filter=20160910Zp9Tm.html
http://www.yqcq.gov.cn/e/space/?userid=157098&yqcq.xml?feed_filter=20160910Bm9Kd.html
http://www.yqcq.gov.cn/e/space/?userid=157099&yqcq.xml?feed_filter=20160910Tm6Pr.html
http://www.yqcq.gov.cn/e/space/?userid=157100&yqcq.xml?feed_filter=20160910Yu8Zq.html
http://www.yqcq.gov.cn/e/space/?userid=157101&yqcq.xml?feed_filter=20160910Rd6Iq.html
http://www.yqcq.gov.cn/e/space/?userid=157102&yqcq.xml?feed_filter=20160910Lf6Fo.html
http://www.yqcq.gov.cn/e/space/?userid=157103&yqcq.xml?feed_filter=20160910Ze7Jw.html
http://www.yqcq.gov.cn/e/space/?userid=157104&yqcq.xml?feed_filter=20160910Nv9So.html
http://www.yqcq.gov.cn/e/space/?userid=157105&yqcq.xml?feed_filter=20160910Ya6Nz.html
http://www.yqcq.gov.cn/e/space/?userid=157106&yqcq.xml?feed_filter=20160910By5Gz.html
http://www.yqcq.gov.cn/e/space/?userid=157107&yqcq.xml?feed_filter=20160910Tk2Rg.html
http://www.yqcq.gov.cn/e/space/?userid=157108&yqcq.xml?feed_filter=20160910Hg8Sl.html
http://www.yqcq.gov.cn/e/space/?userid=157109&yqcq.xml?feed_filter=20160910Ae7Bq.html
http://www.yqcq.gov.cn/e/space/?userid=157110&yqcq.xml?feed_filter=20160910Vr3Rt.html
http://www.yqcq.gov.cn/e/space/?userid=157111&yqcq.xml?feed_filter=20160910Ks5Gz.html
http://www.yqcq.gov.cn/e/space/?userid=157112&yqcq.xml?feed_filter=20160910Qv9Fe.html
http://www.yqcq.gov.cn/e/space/?userid=157113&yqcq.xml?feed_filter=20160910Cw8Qs.html
http://www.yqcq.gov.cn/e/space/?userid=157114&yqcq.xml?feed_filter=20160910Zy4Om.html
http://www.yqcq.gov.cn/e/space/?userid=157115&yqcq.xml?feed_filter=20160910Uo3Za.html
http://www.yqcq.gov.cn/e/space/?userid=157116&yqcq.xml?feed_filter=20160910Vw2Hs.html
http://www.yqcq.gov.cn/e/space/?userid=157117&yqcq.xml?feed_filter=20160910Lp3Iz.html
http://www.yqcq.gov.cn/e/space/?userid=157118&yqcq.xml?feed_filter=20160910Ut3Jg.html
http://www.yqcq.gov.cn/e/space/?userid=157119&yqcq.xml?feed_filter=20160910Hd8Yl.html
http://www.yqcq.gov.cn/e/space/?userid=157120&yqcq.xml?feed_filter=20160910Pu2Ge.html
http://www.yqcq.gov.cn/e/space/?userid=157121&yqcq.xml?feed_filter=20160910Dq8Hp.html
http://www.yqcq.gov.cn/e/space/?userid=157122&yqcq.xml?feed_filter=20160910Dr1Fi.html
http://www.yqcq.gov.cn/e/space/?userid=157123&yqcq.xml?feed_filter=20160910Mv1Rq.html
http://www.yqcq.gov.cn/e/space/?userid=157124&yqcq.xml?feed_filter=20160910Eo6Nj.html
http://www.yqcq.gov.cn/e/space/?userid=157125&yqcq.xml?feed_filter=20160910Uu4Lj.html
http://www.yqcq.gov.cn/e/space/?userid=157126&yqcq.xml?feed_filter=20160910Zj6Pd.html
http://www.yqcq.gov.cn/e/space/?userid=157127&yqcq.xml?feed_filter=20160910Ap3Zi.html
http://www.yqcq.gov.cn/e/space/?userid=157128&yqcq.xml?feed_filter=20160910Qo0Ki.html
http://www.yqcq.gov.cn/e/space/?userid=157129&yqcq.xml?feed_filter=20160910Pm4Ib.html
http://www.yqcq.gov.cn/e/space/?userid=157130&yqcq.xml?feed_filter=20160910Lr2Wx.html
http://www.yqcq.gov.cn/e/space/?userid=157131&yqcq.xml?feed_filter=20160910Lk4Iw.html
http://www.yqcq.gov.cn/e/space/?userid=157132&yqcq.xml?feed_filter=20160910Fk4Hv.html
http://www.yqcq.gov.cn/e/space/?userid=157133&yqcq.xml?feed_filter=20160910Kj2Xd.html
http://www.yqcq.gov.cn/e/space/?userid=157134&yqcq.xml?feed_filter=20160910Qq3Ms.html
http://www.yqcq.gov.cn/e/space/?userid=157135&yqcq.xml?feed_filter=20160910Ef4Py.html
http://www.yqcq.gov.cn/e/space/?userid=157136&yqcq.xml?feed_filter=20160910Sp3Fz.html
http://www.yqcq.gov.cn/e/space/?userid=157137&yqcq.xml?feed_filter=20160910Uf0Id.html
http://www.yqcq.gov.cn/e/space/?userid=157138&yqcq.xml?feed_filter=20160910Xl2Xn.html
http://www.yqcq.gov.cn/e/space/?userid=157139&yqcq.xml?feed_filter=20160910Il8Fq.html
http://www.yqcq.gov.cn/e/space/?userid=157140&yqcq.xml?feed_filter=20160910Qa6Fu.html
http://www.yqcq.gov.cn/e/space/?userid=157141&yqcq.xml?feed_filter=20160910Gl3Xj.html
http://www.yqcq.gov.cn/e/space/?userid=157142&yqcq.xml?feed_filter=20160910Ac6Qt.html
http://www.yqcq.gov.cn/e/space/?userid=157143&yqcq.xml?feed_filter=20160910Zp0Hs.html
http://www.yqcq.gov.cn/e/space/?userid=157144&yqcq.xml?feed_filter=20160910Tl5Fd.html
http://www.yqcq.gov.cn/e/space/?userid=157145&yqcq.xml?feed_filter=20160910Qb2Nd.html
http://www.yqcq.gov.cn/e/space/?userid=157146&yqcq.xml?feed_filter=20160910Cl7Zy.html
http://www.yqcq.gov.cn/e/space/?userid=157147&yqcq.xml?feed_filter=20160910Ru4Ck.html
http://www.yqcq.gov.cn/e/space/?userid=157148&yqcq.xml?feed_filter=20160910Am2By.html
http://www.yqcq.gov.cn/e/space/?userid=157149&yqcq.xml?feed_filter=20160910Ev4Bk.html
http://www.yqcq.gov.cn/e/space/?userid=157150&yqcq.xml?feed_filter=20160910Le4Fe.html
http://www.yqcq.gov.cn/e/space/?userid=157151&yqcq.xml?feed_filter=20160910Kw4Jg.html
http://www.yqcq.gov.cn/e/space/?userid=157152&yqcq.xml?feed_filter=20160910Ug2Il.html
http://www.yqcq.gov.cn/e/space/?userid=157153&yqcq.xml?feed_filter=20160910Km9Td.html
http://www.yqcq.gov.cn/e/space/?userid=157154&yqcq.xml?feed_filter=20160910Xw6Zu.html
http://www.yqcq.gov.cn/e/space/?userid=157155&yqcq.xml?feed_filter=20160910Tp4Zv.html
http://www.yqcq.gov.cn/e/space/?userid=157156&yqcq.xml?feed_filter=20160910Za2Di.html
http://www.yqcq.gov.cn/e/space/?userid=157157&yqcq.xml?feed_filter=20160910Gl1Og.html
http://www.yqcq.gov.cn/e/space/?userid=157158&yqcq.xml?feed_filter=20160910Ve0Vd.html
http://www.yqcq.gov.cn/e/space/?userid=157159&yqcq.xml?feed_filter=20160910Tw0Qp.html
http://www.yqcq.gov.cn/e/space/?userid=157160&yqcq.xml?feed_filter=20160910Zo0Kj.html
http://www.yqcq.gov.cn/e/space/?userid=157161&yqcq.xml?feed_filter=20160910Ca2Ht.html
http://www.yqcq.gov.cn/e/space/?userid=157162&yqcq.xml?feed_filter=20160910Ag1Bd.html
http://www.yqcq.gov.cn/e/space/?userid=157163&yqcq.xml?feed_filter=20160910Oj3Iw.html
http://www.yqcq.gov.cn/e/space/?userid=157164&yqcq.xml?feed_filter=20160910Lc2Py.html
http://www.yqcq.gov.cn/e/space/?userid=157165&yqcq.xml?feed_filter=20160910Qk9Gh.html
http://www.yqcq.gov.cn/e/space/?userid=157166&yqcq.xml?feed_filter=20160910Uv2Qw.html
http://www.yqcq.gov.cn/e/space/?userid=157167&yqcq.xml?feed_filter=20160910Pt9Ad.html
http://www.yqcq.gov.cn/e/space/?userid=157168&yqcq.xml?feed_filter=20160910Rv5Rw.html
http://www.yqcq.gov.cn/e/space/?userid=157169&yqcq.xml?feed_filter=20160910Hv1Pk.html
http://www.yqcq.gov.cn/e/space/?userid=157170&yqcq.xml?feed_filter=20160910Zk7Uz.html
http://www.yqcq.gov.cn/e/space/?userid=157171&yqcq.xml?feed_filter=20160910Ir3Bz.html
http://www.yqcq.gov.cn/e/space/?userid=157172&yqcq.xml?feed_filter=20160910Ay6Jd.html
http://www.yqcq.gov.cn/e/space/?userid=157173&yqcq.xml?feed_filter=20160910Av4Qf.html
http://www.yqcq.gov.cn/e/space/?userid=157174&yqcq.xml?feed_filter=20160910Qj5Vv.html
http://www.yqcq.gov.cn/e/space/?userid=157175&yqcq.xml?feed_filter=20160910Fj2Jo.html
http://www.yqcq.gov.cn/e/space/?userid=157176&yqcq.xml?feed_filter=20160910Dx1Zq.html
http://www.yqcq.gov.cn/e/space/?userid=157177&yqcq.xml?feed_filter=20160910Xb8Gv.html
http://www.yqcq.gov.cn/e/space/?userid=157178&yqcq.xml?feed_filter=20160910Me4Ta.html
http://www.yqcq.gov.cn/e/space/?userid=157179&yqcq.xml?feed_filter=20160910Kx2Im.html
http://www.yqcq.gov.cn/e/space/?userid=157180&yqcq.xml?feed_filter=20160910Hi8Ih.html
http://www.yqcq.gov.cn/e/space/?userid=157181&yqcq.xml?feed_filter=20160910Ya2Si.html
http://www.yqcq.gov.cn/e/space/?userid=157182&yqcq.xml?feed_filter=20160910Xf3Aq.html
http://www.yqcq.gov.cn/e/space/?userid=157183&yqcq.xml?feed_filter=20160910Xo7Po.html
http://www.yqcq.gov.cn/e/space/?userid=157184&yqcq.xml?feed_filter=20160910Hi6Ga.html
http://www.yqcq.gov.cn/e/space/?userid=157185&yqcq.xml?feed_filter=20160910Oz3Ey.html
http://www.yqcq.gov.cn/e/space/?userid=157186&yqcq.xml?feed_filter=20160910Cj4Cq.html
http://www.yqcq.gov.cn/e/space/?userid=157187&yqcq.xml?feed_filter=20160910Qr6Lt.html
http://www.yqcq.gov.cn/e/space/?userid=157188&yqcq.xml?feed_filter=20160910Ym7Hd.html
http://www.yqcq.gov.cn/e/space/?userid=157189&yqcq.xml?feed_filter=20160910Ck7Zk.html
http://www.yqcq.gov.cn/e/space/?userid=157190&yqcq.xml?feed_filter=20160910Hz5Cb.html
http://www.yqcq.gov.cn/e/space/?userid=157191&yqcq.xml?feed_filter=20160910Ye1Wv.html
http://www.yqcq.gov.cn/e/space/?userid=157192&yqcq.xml?feed_filter=20160910Kg4Ac.html
http://www.yqcq.gov.cn/e/space/?userid=157193&yqcq.xml?feed_filter=20160910Oh8Fe.html
http://www.yqcq.gov.cn/e/space/?userid=157194&yqcq.xml?feed_filter=20160910Sn6Sv.html
http://www.yqcq.gov.cn/e/space/?userid=157195&yqcq.xml?feed_filter=20160910Jt8El.html
http://www.yqcq.gov.cn/e/space/?userid=157196&yqcq.xml?feed_filter=20160910Ow8Oh.html
http://www.yqcq.gov.cn/e/space/?userid=157197&yqcq.xml?feed_filter=20160910Iu9Gs.html
http://www.yqcq.gov.cn/e/space/?userid=157198&yqcq.xml?feed_filter=20160910Ic5Fs.html
http://www.yqcq.gov.cn/e/space/?userid=157200&yqcq.xml?feed_filter=20160910Xj7Kj.html
http://www.yqcq.gov.cn/e/space/?userid=157201&yqcq.xml?feed_filter=20160910Dv1Df.html
http://www.yqcq.gov.cn/e/space/?userid=157202&yqcq.xml?feed_filter=20160910Vg1Yo.html
http://www.yqcq.gov.cn/e/space/?userid=157203&yqcq.xml?feed_filter=20160910An4Oz.html
http://www.yqcq.gov.cn/e/space/?userid=157204&yqcq.xml?feed_filter=20160910Vi8Np.html
http://www.yqcq.gov.cn/e/space/?userid=157205&yqcq.xml?feed_filter=20160910Ja7Pm.html
http://www.yqcq.gov.cn/e/space/?userid=157206&yqcq.xml?feed_filter=20160910Ac8Ns.html
http://www.yqcq.gov.cn/e/space/?userid=157207&yqcq.xml?feed_filter=20160910Iu8Hj.html
http://www.yqcq.gov.cn/e/space/?userid=157208&yqcq.xml?feed_filter=20160910Uy3Do.html
http://www.yqcq.gov.cn/e/space/?userid=157209&yqcq.xml?feed_filter=20160910Ax5Or.html
http://www.yqcq.gov.cn/e/space/?userid=157210&yqcq.xml?feed_filter=20160910Hi7Fk.html
http://www.yqcq.gov.cn/e/space/?userid=157211&yqcq.xml?feed_filter=20160910Wl3Cc.html
http://www.yqcq.gov.cn/e/space/?userid=157212&yqcq.xml?feed_filter=20160910Ih1Gp.html
http://www.yqcq.gov.cn/e/space/?userid=157213&yqcq.xml?feed_filter=20160910Jk0Sk.html
http://www.yqcq.gov.cn/e/space/?userid=157214&yqcq.xml?feed_filter=20160910Ac6Pj.html
http://www.yqcq.gov.cn/e/space/?userid=157215&yqcq.xml?feed_filter=20160910Xn2Wy.html
http://www.yqcq.gov.cn/e/space/?userid=157216&yqcq.xml?feed_filter=20160910Ev2Xd.html
http://www.yqcq.gov.cn/e/space/?userid=157217&yqcq.xml?feed_filter=20160910Ka0Bf.html
http://www.yqcq.gov.cn/e/space/?userid=157218&yqcq.xml?feed_filter=20160910Gb9Fl.html
http://www.yqcq.gov.cn/e/space/?userid=157219&yqcq.xml?feed_filter=20160910Ie9Xw.html
http://www.yqcq.gov.cn/e/space/?userid=157220&yqcq.xml?feed_filter=20160910Vs1Rm.html
http://www.yqcq.gov.cn/e/space/?userid=157221&yqcq.xml?feed_filter=20160910My1Sc.html
http://www.yqcq.gov.cn/e/space/?userid=157222&yqcq.xml?feed_filter=20160910Ha3Sb.html
http://www.yqcq.gov.cn/e/space/?userid=157223&yqcq.xml?feed_filter=20160910Ru0Lp.html
http://www.yqcq.gov.cn/e/space/?userid=157224&yqcq.xml?feed_filter=20160910Zd3Gs.html
http://www.yqcq.gov.cn/e/space/?userid=157225&yqcq.xml?feed_filter=20160910Oq2Pf.html
http://www.yqcq.gov.cn/e/space/?userid=157226&yqcq.xml?feed_filter=20160910Qp9Ws.html
http://www.yqcq.gov.cn/e/space/?userid=157227&yqcq.xml?feed_filter=20160910Wx8Wr.html
http://www.yqcq.gov.cn/e/space/?userid=157228&yqcq.xml?feed_filter=20160910Wm4Gn.html
http://www.yqcq.gov.cn/e/space/?userid=157229&yqcq.xml?feed_filter=20160910Pa6Mo.html
http://www.yqcq.gov.cn/e/space/?userid=157230&yqcq.xml?feed_filter=20160910Ez0Bm.html
http://www.yqcq.gov.cn/e/space/?userid=157231&yqcq.xml?feed_filter=20160910Xd2Qo.html
http://www.yqcq.gov.cn/e/space/?userid=157232&yqcq.xml?feed_filter=20160910Ms0Ka.html
http://www.yqcq.gov.cn/e/space/?userid=157233&yqcq.xml?feed_filter=20160910Ap5Ii.html
http://www.yqcq.gov.cn/e/space/?userid=157234&yqcq.xml?feed_filter=20160910Bc7Sn.html
http://www.yqcq.gov.cn/e/space/?userid=157236&yqcq.xml?feed_filter=20160910Oc9Nf.html
http://www.yqcq.gov.cn/e/space/?userid=157237&yqcq.xml?feed_filter=20160910Ce8Ge.html
http://www.yqcq.gov.cn/e/space/?userid=157238&yqcq.xml?feed_filter=20160910Ky3Gv.html
http://www.yqcq.gov.cn/e/space/?userid=157239&yqcq.xml?feed_filter=20160910Fm9Oq.html
http://www.yqcq.gov.cn/e/space/?userid=157240&yqcq.xml?feed_filter=20160910Nt9Qz.html
http://www.yqcq.gov.cn/e/space/?userid=157241&yqcq.xml?feed_filter=20160910Jk0Xt.html
http://www.yqcq.gov.cn/e/space/?userid=157242&yqcq.xml?feed_filter=20160910Dl9Wy.html
http://www.yqcq.gov.cn/e/space/?userid=157243&yqcq.xml?feed_filter=20160910Ld3Ip.html
http://www.yqcq.gov.cn/e/space/?userid=157244&yqcq.xml?feed_filter=20160910Hy4Bm.html
http://www.yqcq.gov.cn/e/space/?userid=157245&yqcq.xml?feed_filter=20160910De4Ob.html
http://www.yqcq.gov.cn/e/space/?userid=157246&yqcq.xml?feed_filter=20160910Mk6Ox.html
http://www.yqcq.gov.cn/e/space/?userid=157247&yqcq.xml?feed_filter=20160910Sl7Sx.html
http://www.yqcq.gov.cn/e/space/?userid=157248&yqcq.xml?feed_filter=20160910Mk8Ru.html
http://www.yqcq.gov.cn/e/space/?userid=157249&yqcq.xml?feed_filter=20160910Vb8Hp.html
http://www.yqcq.gov.cn/e/space/?userid=157250&yqcq.xml?feed_filter=20160910Eq6Ja.html
http://www.yqcq.gov.cn/e/space/?userid=157251&yqcq.xml?feed_filter=20160910Uu0Wz.html
http://www.yqcq.gov.cn/e/space/?userid=157252&yqcq.xml?feed_filter=20160910Yp8Le.html
http://www.yqcq.gov.cn/e/space/?userid=157253&yqcq.xml?feed_filter=20160910Xc2Iy.html
http://www.yqcq.gov.cn/e/space/?userid=157254&yqcq.xml?feed_filter=20160910Ls1Ix.html
http://www.yqcq.gov.cn/e/space/?userid=157255&yqcq.xml?feed_filter=20160910Pz0Ky.html
http://www.yqcq.gov.cn/e/space/?userid=157256&yqcq.xml?feed_filter=20160910Sh7Xb.html
http://www.yqcq.gov.cn/e/space/?userid=157257&yqcq.xml?feed_filter=20160910Dv8Ug.html
http://www.yqcq.gov.cn/e/space/?userid=157258&yqcq.xml?feed_filter=20160910Bs4Ba.html
http://www.yqcq.gov.cn/e/space/?userid=157259&yqcq.xml?feed_filter=20160910Qq5Fz.html
http://www.yqcq.gov.cn/e/space/?userid=157260&yqcq.xml?feed_filter=20160910Fq9Lr.html
http://www.yqcq.gov.cn/e/space/?userid=157261&yqcq.xml?feed_filter=20160910Bi9Wm.html
http://www.yqcq.gov.cn/e/space/?userid=157262&yqcq.xml?feed_filter=20160910Xy6Bt.html
http://www.yqcq.gov.cn/e/space/?userid=157263&yqcq.xml?feed_filter=20160910Ef4Gv.html
http://www.yqcq.gov.cn/e/space/?userid=157264&yqcq.xml?feed_filter=20160910Vy1Yu.html
http://www.yqcq.gov.cn/e/space/?userid=157265&yqcq.xml?feed_filter=20160910Zo9Qk.html
http://www.yqcq.gov.cn/e/space/?userid=157266&yqcq.xml?feed_filter=20160910Jv7Ex.html
http://www.yqcq.gov.cn/e/space/?userid=157267&yqcq.xml?feed_filter=20160910Hl4Hj.html
http://www.yqcq.gov.cn/e/space/?userid=157268&yqcq.xml?feed_filter=20160910Id4Ir.html
http://www.yqcq.gov.cn/e/space/?userid=157269&yqcq.xml?feed_filter=20160910Vd5Qi.html
http://www.yqcq.gov.cn/e/space/?userid=157270&yqcq.xml?feed_filter=20160910Ti1Ym.html
http://www.yqcq.gov.cn/e/space/?userid=157271&yqcq.xml?feed_filter=20160910Zt3Bx.html
http://www.yqcq.gov.cn/e/space/?userid=157272&yqcq.xml?feed_filter=20160910Lw6Xj.html
http://www.yqcq.gov.cn/e/space/?userid=157273&yqcq.xml?feed_filter=20160910Gj6Rb.html
http://www.yqcq.gov.cn/e/space/?userid=157274&yqcq.xml?feed_filter=20160910Dv1Ga.html
http://www.yqcq.gov.cn/e/space/?userid=157275&yqcq.xml?feed_filter=20160910Bl1Zb.html
http://www.yqcq.gov.cn/e/space/?userid=157276&yqcq.xml?feed_filter=20160910Hz7Re.html
http://www.yqcq.gov.cn/e/space/?userid=157277&yqcq.xml?feed_filter=20160910Mi2Gg.html
http://www.yqcq.gov.cn/e/space/?userid=157278&yqcq.xml?feed_filter=20160910Jq8Pe.html
http://www.yqcq.gov.cn/e/space/?userid=157280&yqcq.xml?feed_filter=20160910Ks5Tw.html
http://www.yqcq.gov.cn/e/space/?userid=157282&yqcq.xml?feed_filter=20160910Ef3Uu.html
http://www.yqcq.gov.cn/e/space/?userid=157283&yqcq.xml?feed_filter=20160910Ow3Lh.html
http://www.yqcq.gov.cn/e/space/?userid=157284&yqcq.xml?feed_filter=20160910Fo4Vl.html
http://www.yqcq.gov.cn/e/space/?userid=157285&yqcq.xml?feed_filter=20160910Mu4De.html
http://www.yqcq.gov.cn/e/space/?userid=157286&yqcq.xml?feed_filter=20160910Qi1Qw.html
http://www.yqcq.gov.cn/e/space/?userid=157287&yqcq.xml?feed_filter=20160910Ib2Ew.html
http://www.yqcq.gov.cn/e/space/?userid=157288&yqcq.xml?feed_filter=20160910Ym1Mv.html
http://www.yqcq.gov.cn/e/space/?userid=157289&yqcq.xml?feed_filter=20160910Px4Ds.html
http://www.yqcq.gov.cn/e/space/?userid=157290&yqcq.xml?feed_filter=20160910Qu6Kd.html
http://www.yqcq.gov.cn/e/space/?userid=157291&yqcq.xml?feed_filter=20160910Em8Wd.html
http://www.yqcq.gov.cn/e/space/?userid=157292&yqcq.xml?feed_filter=20160910Ge0Dn.html
http://www.yqcq.gov.cn/e/space/?userid=157293&yqcq.xml?feed_filter=20160910Oi8Yb.html
http://www.yqcq.gov.cn/e/space/?userid=157294&yqcq.xml?feed_filter=20160910Jt8Ud.html
http://www.yqcq.gov.cn/e/space/?userid=157295&yqcq.xml?feed_filter=20160910Po1Sy.html
http://www.yqcq.gov.cn/e/space/?userid=157296&yqcq.xml?feed_filter=20160910Ug4Xe.html
http://www.yqcq.gov.cn/e/space/?userid=157297&yqcq.xml?feed_filter=20160910Yg8Vn.html
http://www.yqcq.gov.cn/e/space/?userid=157298&yqcq.xml?feed_filter=20160910Tv4Ri.html
http://www.yqcq.gov.cn/e/space/?userid=157299&yqcq.xml?feed_filter=20160910Sl3Un.html
http://www.yqcq.gov.cn/e/space/?userid=157300&yqcq.xml?feed_filter=20160910Xn3By.html
http://www.yqcq.gov.cn/e/space/?userid=157301&yqcq.xml?feed_filter=20160910Fg8Ii.html
http://www.yqcq.gov.cn/e/space/?userid=157302&yqcq.xml?feed_filter=20160910Bq8Sr.html
http://www.yqcq.gov.cn/e/space/?userid=157303&yqcq.xml?feed_filter=20160910Ip6Id.html
http://www.yqcq.gov.cn/e/space/?userid=157304&yqcq.xml?feed_filter=20160910Vw3Av.html
http://www.yqcq.gov.cn/e/space/?userid=157305&yqcq.xml?feed_filter=20160910Zd1Sp.html
http://www.yqcq.gov.cn/e/space/?userid=157306&yqcq.xml?feed_filter=20160910Vv6Ln.html
http://www.yqcq.gov.cn/e/space/?userid=157307&yqcq.xml?feed_filter=20160910Vf9Lo.html
http://www.yqcq.gov.cn/e/space/?userid=157308&yqcq.xml?feed_filter=20160910It3Lr.html
http://www.yqcq.gov.cn/e/space/?userid=157309&yqcq.xml?feed_filter=20160910Bi0Dc.html
http://www.yqcq.gov.cn/e/space/?userid=157310&yqcq.xml?feed_filter=20160910Ho2Om.html
http://www.yqcq.gov.cn/e/space/?userid=157311&yqcq.xml?feed_filter=20160910Jj3Qc.html
http://www.yqcq.gov.cn/e/space/?userid=157312&yqcq.xml?feed_filter=20160910Ju6Bn.html
http://www.yqcq.gov.cn/e/space/?userid=157314&yqcq.xml?feed_filter=20160910Rw0Hh.html
http://www.yqcq.gov.cn/e/space/?userid=157315&yqcq.xml?feed_filter=20160910Cy8Yq.html
http://www.yqcq.gov.cn/e/space/?userid=157316&yqcq.xml?feed_filter=20160910Aq9Jg.html
http://www.yqcq.gov.cn/e/space/?userid=157317&yqcq.xml?feed_filter=20160910Ok2We.html
http://www.yqcq.gov.cn/e/space/?userid=157318&yqcq.xml?feed_filter=20160910Sl0Is.html
http://www.yqcq.gov.cn/e/space/?userid=157319&yqcq.xml?feed_filter=20160910Tj0Fy.html
http://www.yqcq.gov.cn/e/space/?userid=157320&yqcq.xml?feed_filter=20160910Rb7Mp.html
http://www.yqcq.gov.cn/e/space/?userid=157321&yqcq.xml?feed_filter=20160910Po7Xy.html
http://www.yqcq.gov.cn/e/space/?userid=157322&yqcq.xml?feed_filter=20160910Rw9Mj.html
http://www.yqcq.gov.cn/e/space/?userid=157324&yqcq.xml?feed_filter=20160910Wh5Rc.html
http://www.yqcq.gov.cn/e/space/?userid=157325&yqcq.xml?feed_filter=20160910Ro7Ch.html
http://www.yqcq.gov.cn/e/space/?userid=157326&yqcq.xml?feed_filter=20160910Oq0Ek.html
http://www.yqcq.gov.cn/e/space/?userid=157327&yqcq.xml?feed_filter=20160910Cl6Rm.html
http://www.yqcq.gov.cn/e/space/?userid=157328&yqcq.xml?feed_filter=20160910Zo3Qt.html
http://www.yqcq.gov.cn/e/space/?userid=157329&yqcq.xml?feed_filter=20160910Ov4Cy.html
http://www.yqcq.gov.cn/e/space/?userid=157330&yqcq.xml?feed_filter=20160910Xq1Tn.html
http://www.yqcq.gov.cn/e/space/?userid=157331&yqcq.xml?feed_filter=20160910Nq5Eu.html
http://www.yqcq.gov.cn/e/space/?userid=157332&yqcq.xml?feed_filter=20160910Cm1Gg.html
http://www.yqcq.gov.cn/e/space/?userid=157333&yqcq.xml?feed_filter=20160910Jd2Wj.html
http://www.yqcq.gov.cn/e/space/?userid=157334&yqcq.xml?feed_filter=20160910Eh7Pt.html
http://www.yqcq.gov.cn/e/space/?userid=157335&yqcq.xml?feed_filter=20160910Um9Ld.html
http://www.yqcq.gov.cn/e/space/?userid=157336&yqcq.xml?feed_filter=20160910Hh3Px.html
http://www.yqcq.gov.cn/e/space/?userid=157337&yqcq.xml?feed_filter=20160910Ge8Qn.html
http://www.yqcq.gov.cn/e/space/?userid=157338&yqcq.xml?feed_filter=20160910Wg7Vm.html
http://www.yqcq.gov.cn/e/space/?userid=157339&yqcq.xml?feed_filter=20160910Fk4Fq.html
http://www.yqcq.gov.cn/e/space/?userid=157340&yqcq.xml?feed_filter=20160910Iq5Wk.html
http://www.yqcq.gov.cn/e/space/?userid=157341&yqcq.xml?feed_filter=20160910Rx9Fe.html
http://www.yqcq.gov.cn/e/space/?userid=157342&yqcq.xml?feed_filter=20160910Bf3Jw.html
http://www.yqcq.gov.cn/e/space/?userid=157343&yqcq.xml?feed_filter=20160910Ms0Ek.html
http://www.yqcq.gov.cn/e/space/?userid=157344&yqcq.xml?feed_filter=20160910Qj9Ju.html
http://www.yqcq.gov.cn/e/space/?userid=157345&yqcq.xml?feed_filter=20160910Uz9Br.html
http://www.yqcq.gov.cn/e/space/?userid=157346&yqcq.xml?feed_filter=20160910Km9Ry.html
http://www.yqcq.gov.cn/e/space/?userid=157347&yqcq.xml?feed_filter=20160910Hh2Cf.html
http://www.yqcq.gov.cn/e/space/?userid=157348&yqcq.xml?feed_filter=20160910Xx1Ba.html
http://www.yqcq.gov.cn/e/space/?userid=157349&yqcq.xml?feed_filter=20160910Xz2Rk.html
http://www.yqcq.gov.cn/e/space/?userid=157350&yqcq.xml?feed_filter=20160910Oo4Av.html
http://www.yqcq.gov.cn/e/space/?userid=157351&yqcq.xml?feed_filter=20160910Tj1Cx.html
http://www.yqcq.gov.cn/e/space/?userid=157352&yqcq.xml?feed_filter=20160910Xa3Fc.html
http://www.yqcq.gov.cn/e/space/?userid=157353&yqcq.xml?feed_filter=20160910Ii8Ot.html
http://www.yqcq.gov.cn/e/space/?userid=157354&yqcq.xml?feed_filter=20160910Dq1Nx.html
http://www.yqcq.gov.cn/e/space/?userid=157355&yqcq.xml?feed_filter=20160910Du3Vx.html
http://www.yqcq.gov.cn/e/space/?userid=157356&yqcq.xml?feed_filter=20160910Bm4Ja.html
http://www.yqcq.gov.cn/e/space/?userid=157357&yqcq.xml?feed_filter=20160910Ap0El.html
http://www.yqcq.gov.cn/e/space/?userid=157358&yqcq.xml?feed_filter=20160910Nm3Cr.html
http://www.yqcq.gov.cn/e/space/?userid=157359&yqcq.xml?feed_filter=20160910Nf8Ck.html
http://www.yqcq.gov.cn/e/space/?userid=157360&yqcq.xml?feed_filter=20160910Cl4Xv.html
http://www.yqcq.gov.cn/e/space/?userid=157361&yqcq.xml?feed_filter=20160910Fn3Zv.html
http://www.yqcq.gov.cn/e/space/?userid=157362&yqcq.xml?feed_filter=20160910Rk1Gc.html
http://www.yqcq.gov.cn/e/space/?userid=157363&yqcq.xml?feed_filter=20160910Xv5Xk.html
http://www.yqcq.gov.cn/e/space/?userid=157364&yqcq.xml?feed_filter=20160910Kf2Ae.html
http://www.yqcq.gov.cn/e/space/?userid=157365&yqcq.xml?feed_filter=20160910Yg6Vq.html
http://www.yqcq.gov.cn/e/space/?userid=157367&yqcq.xml?feed_filter=20160910Xf8Va.html
http://www.yqcq.gov.cn/e/space/?userid=157368&yqcq.xml?feed_filter=20160910Kn9Av.html
http://www.yqcq.gov.cn/e/space/?userid=157369&yqcq.xml?feed_filter=20160910Ls8Aj.html
http://www.yqcq.gov.cn/e/space/?userid=157370&yqcq.xml?feed_filter=20160910Rg1Gw.html
http://www.yqcq.gov.cn/e/space/?userid=157371&yqcq.xml?feed_filter=20160910Xc5Rd.html
http://www.yqcq.gov.cn/e/space/?userid=157372&yqcq.xml?feed_filter=20160910Zv2Dj.html
http://www.yqcq.gov.cn/e/space/?userid=157373&yqcq.xml?feed_filter=20160910Gh8Nc.html
http://www.yqcq.gov.cn/e/space/?userid=157374&yqcq.xml?feed_filter=20160910Ok6Yz.html
http://www.yqcq.gov.cn/e/space/?userid=157375&yqcq.xml?feed_filter=20160910Bn2Bp.html
http://www.yqcq.gov.cn/e/space/?userid=157376&yqcq.xml?feed_filter=20160910Sj9Th.html
http://www.yqcq.gov.cn/e/space/?userid=157377&yqcq.xml?feed_filter=20160910Yk7Nk.html
http://www.yqcq.gov.cn/e/space/?userid=157378&yqcq.xml?feed_filter=20160910Tu6Fp.html
http://www.yqcq.gov.cn/e/space/?userid=157379&yqcq.xml?feed_filter=20160910Fc7Ul.html
http://www.yqcq.gov.cn/e/space/?userid=157380&yqcq.xml?feed_filter=20160910Xp0Vo.html
http://www.yqcq.gov.cn/e/space/?userid=157381&yqcq.xml?feed_filter=20160910Nm2Mg.html
http://www.yqcq.gov.cn/e/space/?userid=157382&yqcq.xml?feed_filter=20160910Oh7Kn.html
http://www.yqcq.gov.cn/e/space/?userid=157383&yqcq.xml?feed_filter=20160910Vq5Su.html
http://www.yqcq.gov.cn/e/space/?userid=157384&yqcq.xml?feed_filter=20160910Rg3Nd.html
http://www.yqcq.gov.cn/e/space/?userid=157385&yqcq.xml?feed_filter=20160910Dz2Wq.html
http://www.yqcq.gov.cn/e/space/?userid=157386&yqcq.xml?feed_filter=20160910Pq6Us.html
http://www.yqcq.gov.cn/e/space/?userid=157387&yqcq.xml?feed_filter=20160910Ua5Ja.html
http://www.yqcq.gov.cn/e/space/?userid=157388&yqcq.xml?feed_filter=20160910Zt5Eq.html
http://www.yqcq.gov.cn/e/space/?userid=157389&yqcq.xml?feed_filter=20160910Dr5Co.html
http://www.yqcq.gov.cn/e/space/?userid=157390&yqcq.xml?feed_filter=20160910Nj6Jy.html
http://www.yqcq.gov.cn/e/space/?userid=157391&yqcq.xml?feed_filter=20160910Wa1Rq.html
http://www.yqcq.gov.cn/e/space/?userid=157392&yqcq.xml?feed_filter=20160910Xk9Xj.html
http://www.yqcq.gov.cn/e/space/?userid=157393&yqcq.xml?feed_filter=20160910As5Yb.html
http://www.yqcq.gov.cn/e/space/?userid=157394&yqcq.xml?feed_filter=20160910Oo3Ln.html
http://www.yqcq.gov.cn/e/space/?userid=157395&yqcq.xml?feed_filter=20160910Qy1Ap.html
http://www.yqcq.gov.cn/e/space/?userid=157396&yqcq.xml?feed_filter=20160910Dj5Ah.html
http://www.yqcq.gov.cn/e/space/?userid=157397&yqcq.xml?feed_filter=20160910Cs6Xu.html
http://www.yqcq.gov.cn/e/space/?userid=157398&yqcq.xml?feed_filter=20160910Am5Ty.html
http://www.yqcq.gov.cn/e/space/?userid=157399&yqcq.xml?feed_filter=20160910Vf4Ct.html
http://www.yqcq.gov.cn/e/space/?userid=157400&yqcq.xml?feed_filter=20160910Sz7Ji.html
http://www.yqcq.gov.cn/e/space/?userid=157401&yqcq.xml?feed_filter=20160910Wh1Aa.html
http://www.yqcq.gov.cn/e/space/?userid=157402&yqcq.xml?feed_filter=20160910Om5Em.html
http://www.yqcq.gov.cn/e/space/?userid=157403&yqcq.xml?feed_filter=20160910Zc5Qu.html
http://www.yqcq.gov.cn/e/space/?userid=157404&yqcq.xml?feed_filter=20160910Qj3Gf.html
http://www.yqcq.gov.cn/e/space/?userid=157405&yqcq.xml?feed_filter=20160910Yc9Do.html
http://www.yqcq.gov.cn/e/space/?userid=157406&yqcq.xml?feed_filter=20160910Tm3Kx.html
http://www.yqcq.gov.cn/e/space/?userid=157407&yqcq.xml?feed_filter=20160910Oj2Ow.html
http://www.yqcq.gov.cn/e/space/?userid=157408&yqcq.xml?feed_filter=20160910Av1El.html
http://www.yqcq.gov.cn/e/space/?userid=157409&yqcq.xml?feed_filter=20160910Oz0Gh.html
http://www.yqcq.gov.cn/e/space/?userid=157410&yqcq.xml?feed_filter=20160910Ne9To.html
http://www.yqcq.gov.cn/e/space/?userid=157411&yqcq.xml?feed_filter=20160910Dy1Ia.html
http://www.yqcq.gov.cn/e/space/?userid=157412&yqcq.xml?feed_filter=20160910Dw7Uc.html
http://www.yqcq.gov.cn/e/space/?userid=157413&yqcq.xml?feed_filter=20160910Rr1Qi.html
http://www.yqcq.gov.cn/e/space/?userid=157414&yqcq.xml?feed_filter=20160910Pn3Ov.html
http://www.yqcq.gov.cn/e/space/?userid=157415&yqcq.xml?feed_filter=20160910Si9Hb.html
http://www.yqcq.gov.cn/e/space/?userid=157416&yqcq.xml?feed_filter=20160910Lk0Wa.html
http://www.yqcq.gov.cn/e/space/?userid=157417&yqcq.xml?feed_filter=20160910Ug5Fn.html
http://www.yqcq.gov.cn/e/space/?userid=157418&yqcq.xml?feed_filter=20160910Mn9Mk.html
http://www.yqcq.gov.cn/e/space/?userid=157419&yqcq.xml?feed_filter=20160910Zk5Uh.html
http://www.yqcq.gov.cn/e/space/?userid=157420&yqcq.xml?feed_filter=20160910Wr8Dq.html
http://www.yqcq.gov.cn/e/space/?userid=157421&yqcq.xml?feed_filter=20160910Nw8Pa.html
http://www.yqcq.gov.cn/e/space/?userid=157422&yqcq.xml?feed_filter=20160910Wc3Lk.html
http://www.yqcq.gov.cn/e/space/?userid=157423&yqcq.xml?feed_filter=20160910Qg3Dh.html
http://www.yqcq.gov.cn/e/space/?userid=157424&yqcq.xml?feed_filter=20160910Xz3Rk.html
http://www.yqcq.gov.cn/e/space/?userid=157425&yqcq.xml?feed_filter=20160910Cr0Mk.html
http://www.yqcq.gov.cn/e/space/?userid=157426&yqcq.xml?feed_filter=20160910Pa0Du.html
http://www.yqcq.gov.cn/e/space/?userid=157427&yqcq.xml?feed_filter=20160910Nw1Ch.html
http://www.yqcq.gov.cn/e/space/?userid=157428&yqcq.xml?feed_filter=20160910Ds8Em.html
http://www.yqcq.gov.cn/e/space/?userid=157429&yqcq.xml?feed_filter=20160910Uz3Qk.html
http://www.yqcq.gov.cn/e/space/?userid=157430&yqcq.xml?feed_filter=20160910Tl8Xi.html
http://www.yqcq.gov.cn/e/space/?userid=157431&yqcq.xml?feed_filter=20160910Mr8Ax.html
http://www.yqcq.gov.cn/e/space/?userid=157432&yqcq.xml?feed_filter=20160910Ay6Ma.html
http://www.yqcq.gov.cn/e/space/?userid=157433&yqcq.xml?feed_filter=20160910Mi6Ny.html
http://www.yqcq.gov.cn/e/space/?userid=157435&yqcq.xml?feed_filter=20160910Fv2Sa.html
http://www.yqcq.gov.cn/e/space/?userid=157436&yqcq.xml?feed_filter=20160910Sy9Gl.html
http://www.yqcq.gov.cn/e/space/?userid=157437&yqcq.xml?feed_filter=20160910Eu9Nk.html
http://www.yqcq.gov.cn/e/space/?userid=157438&yqcq.xml?feed_filter=20160910Ll4Yu.html
http://www.yqcq.gov.cn/e/space/?userid=157439&yqcq.xml?feed_filter=20160910Qj5Wa.html
http://www.yqcq.gov.cn/e/space/?userid=157440&yqcq.xml?feed_filter=20160910Pt0Ur.html
http://www.yqcq.gov.cn/e/space/?userid=157441&yqcq.xml?feed_filter=20160910Cw1De.html
http://www.yqcq.gov.cn/e/space/?userid=157442&yqcq.xml?feed_filter=20160910Mc3Pn.html
http://www.yqcq.gov.cn/e/space/?userid=157443&yqcq.xml?feed_filter=20160910Ol5Re.html
http://www.yqcq.gov.cn/e/space/?userid=157444&yqcq.xml?feed_filter=20160910Cs9Sr.html
http://www.yqcq.gov.cn/e/space/?userid=157445&yqcq.xml?feed_filter=20160910Ra9Zj.html
http://www.yqcq.gov.cn/e/space/?userid=157446&yqcq.xml?feed_filter=20160910Sc8Bg.html
http://www.yqcq.gov.cn/e/space/?userid=157447&yqcq.xml?feed_filter=20160910Ka8Es.html
http://www.yqcq.gov.cn/e/space/?userid=157448&yqcq.xml?feed_filter=20160910Yq5Zg.html
http://www.yqcq.gov.cn/e/space/?userid=157450&yqcq.xml?feed_filter=20160910Bx0Ng.html
http://www.yqcq.gov.cn/e/space/?userid=157451&yqcq.xml?feed_filter=20160910Mw1Hv.html
http://www.yqcq.gov.cn/e/space/?userid=157452&yqcq.xml?feed_filter=20160910Yt9Xx.html
http://www.yqcq.gov.cn/e/space/?userid=157453&yqcq.xml?feed_filter=20160910Rc3Kk.html
http://www.yqcq.gov.cn/e/space/?userid=157454&yqcq.xml?feed_filter=20160910Mq0Ud.html
http://www.yqcq.gov.cn/e/space/?userid=157455&yqcq.xml?feed_filter=20160910Wu8Nc.html
http://www.yqcq.gov.cn/e/space/?userid=157456&yqcq.xml?feed_filter=20160910Qg4Jf.html
http://www.yqcq.gov.cn/e/space/?userid=157457&yqcq.xml?feed_filter=20160910Bw9Ni.html
http://www.yqcq.gov.cn/e/space/?userid=157458&yqcq.xml?feed_filter=20160910Vf4Eg.html
http://www.yqcq.gov.cn/e/space/?userid=157459&yqcq.xml?feed_filter=20160910Rs5To.html
http://www.yqcq.gov.cn/e/space/?userid=157460&yqcq.xml?feed_filter=20160910An7Jo.html
http://www.yqcq.gov.cn/e/space/?userid=157461&yqcq.xml?feed_filter=20160910Jx1Fq.html
http://www.yqcq.gov.cn/e/space/?userid=157462&yqcq.xml?feed_filter=20160910Hd2Li.html
http://www.yqcq.gov.cn/e/space/?userid=157463&yqcq.xml?feed_filter=20160910Fi4Ok.html
http://www.yqcq.gov.cn/e/space/?userid=157464&yqcq.xml?feed_filter=20160910Sf8Rd.html
http://www.yqcq.gov.cn/e/space/?userid=157465&yqcq.xml?feed_filter=20160910Px8Yo.html
http://www.yqcq.gov.cn/e/space/?userid=157466&yqcq.xml?feed_filter=20160910Ai0Af.html
http://www.yqcq.gov.cn/e/space/?userid=157467&yqcq.xml?feed_filter=20160910In9Ok.html
http://www.yqcq.gov.cn/e/space/?userid=157470&yqcq.xml?feed_filter=20160910Qr7Nf.html
http://www.yqcq.gov.cn/e/space/?userid=157474&yqcq.xml?feed_filter=20160910Tg4Yc.html
http://www.yqcq.gov.cn/e/space/?userid=157476&yqcq.xml?feed_filter=20160910Qi9Gi.html
http://www.yqcq.gov.cn/e/space/?userid=157479&yqcq.xml?feed_filter=20160910Jy7Su.html
http://www.yqcq.gov.cn/e/space/?userid=157482&yqcq.xml?feed_filter=20160910Vd6Io.html
http://www.yqcq.gov.cn/e/space/?userid=157483&yqcq.xml?feed_filter=20160910Fz8Ca.html
http://www.yqcq.gov.cn/e/space/?userid=157486&yqcq.xml?feed_filter=20160910Yk4Ye.html
http://www.yqcq.gov.cn/e/space/?userid=157487&yqcq.xml?feed_filter=20160910Ll0Pb.html
http://www.yqcq.gov.cn/e/space/?userid=157488&yqcq.xml?feed_filter=20160910Lh6Hm.html
http://www.yqcq.gov.cn/e/space/?userid=157489&yqcq.xml?feed_filter=20160910Vt3Xc.html
http://www.yqcq.gov.cn/e/space/?userid=157491&yqcq.xml?feed_filter=20160910Nl7Sv.html
http://www.yqcq.gov.cn/e/space/?userid=157492&yqcq.xml?feed_filter=20160910Ol5Ms.html
http://www.yqcq.gov.cn/e/space/?userid=157493&yqcq.xml?feed_filter=20160910Ou3Ee.html
http://www.yqcq.gov.cn/e/space/?userid=157495&yqcq.xml?feed_filter=20160910To3Ft.html
http://www.yqcq.gov.cn/e/space/?userid=157496&yqcq.xml?feed_filter=20160910Nh2Cd.html
http://www.yqcq.gov.cn/e/space/?userid=157497&yqcq.xml?feed_filter=20160910Ob4Sf.html
http://www.yqcq.gov.cn/e/space/?userid=157499&yqcq.xml?feed_filter=20160910By6Nv.html
http://www.yqcq.gov.cn/e/space/?userid=157500&yqcq.xml?feed_filter=20160910Wu8Gr.html
http://www.yqcq.gov.cn/e/space/?userid=157501&yqcq.xml?feed_filter=20160910Eo3Af.html
http://www.yqcq.gov.cn/e/space/?userid=157503&yqcq.xml?feed_filter=20160910Ur3Ec.html
http://www.yqcq.gov.cn/e/space/?userid=157504&yqcq.xml?feed_filter=20160910Hj8Lh.html
http://www.yqcq.gov.cn/e/space/?userid=157505&yqcq.xml?feed_filter=20160910Om9Ob.html
http://www.yqcq.gov.cn/e/space/?userid=157506&yqcq.xml?feed_filter=20160910Rw0Jd.html
http://www.yqcq.gov.cn/e/space/?userid=157508&yqcq.xml?feed_filter=20160910Jl6Mo.html
http://www.yqcq.gov.cn/e/space/?userid=157509&yqcq.xml?feed_filter=20160910Cd3Vf.html
http://www.yqcq.gov.cn/e/space/?userid=157510&yqcq.xml?feed_filter=20160910Cz3Xn.html
http://www.yqcq.gov.cn/e/space/?userid=157511&yqcq.xml?feed_filter=20160910Oh9Ct.html
http://www.yqcq.gov.cn/e/space/?userid=157513&yqcq.xml?feed_filter=20160910Zt7Ps.html
http://www.yqcq.gov.cn/e/space/?userid=157514&yqcq.xml?feed_filter=20160910Xk3Jz.html
http://www.yqcq.gov.cn/e/space/?userid=157515&yqcq.xml?feed_filter=20160910Xp4Pz.html
http://www.yqcq.gov.cn/e/space/?userid=157518&yqcq.xml?feed_filter=20160910Sf3Jp.html
http://www.yqcq.gov.cn/e/space/?userid=157521&yqcq.xml?feed_filter=20160910Lm2Mu.html
http://www.yqcq.gov.cn/e/space/?userid=157523&yqcq.xml?feed_filter=20160910Nq7Zz.html
http://www.yqcq.gov.cn/e/space/?userid=157527&yqcq.xml?feed_filter=20160910Nk2Bb.html
http://www.yqcq.gov.cn/e/space/?userid=157528&yqcq.xml?feed_filter=20160910Qt6Vp.html
http://www.yqcq.gov.cn/e/space/?userid=157531&yqcq.xml?feed_filter=20160910Jh4Ro.html
http://www.yqcq.gov.cn/e/space/?userid=157533&yqcq.xml?feed_filter=20160910As4Uy.html
http://www.yqcq.gov.cn/e/space/?userid=157534&yqcq.xml?feed_filter=20160910At4Fx.html
http://www.yqcq.gov.cn/e/space/?userid=157536&yqcq.xml?feed_filter=20160910Of6Ht.html
http://www.yqcq.gov.cn/e/space/?userid=157537&yqcq.xml?feed_filter=20160910Ra9Wx.html
http://www.yqcq.gov.cn/e/space/?userid=157539&yqcq.xml?feed_filter=20160910Ob0Zf.html
http://www.yqcq.gov.cn/e/space/?userid=157540&yqcq.xml?feed_filter=20160910Jz3Fx.html
http://www.yqcq.gov.cn/e/space/?userid=157541&yqcq.xml?feed_filter=20160910Qb4As.html
http://www.yqcq.gov.cn/e/space/?userid=157543&yqcq.xml?feed_filter=20160910Qs9Yi.html
http://www.yqcq.gov.cn/e/space/?userid=157544&yqcq.xml?feed_filter=20160910Nd9Yf.html
http://www.yqcq.gov.cn/e/space/?userid=157545&yqcq.xml?feed_filter=20160910Wc1Iw.html
http://www.yqcq.gov.cn/e/space/?userid=157547&yqcq.xml?feed_filter=20160910Ua7Ps.html
http://www.yqcq.gov.cn/e/space/?userid=157548&yqcq.xml?feed_filter=20160910To1Oz.html
http://www.yqcq.gov.cn/e/space/?userid=157550&yqcq.xml?feed_filter=20160910Mu7Po.html
http://www.yqcq.gov.cn/e/space/?userid=157551&yqcq.xml?feed_filter=20160910Fu2Rc.html
http://www.yqcq.gov.cn/e/space/?userid=157552&yqcq.xml?feed_filter=20160910Gn3Hu.html
http://www.yqcq.gov.cn/e/space/?userid=157554&yqcq.xml?feed_filter=20160910Io8Ga.html
http://www.yqcq.gov.cn/e/space/?userid=157557&yqcq.xml?feed_filter=20160910Cf3Bk.html
http://www.yqcq.gov.cn/e/space/?userid=157558&yqcq.xml?feed_filter=20160910Um5Me.html
http://www.yqcq.gov.cn/e/space/?userid=157559&yqcq.xml?feed_filter=20160910Ke2Yv.html
http://www.yqcq.gov.cn/e/space/?userid=157561&yqcq.xml?feed_filter=20160910Fg4Sa.html
http://www.yqcq.gov.cn/e/space/?userid=157562&yqcq.xml?feed_filter=20160910Pk8Dj.html
http://www.yqcq.gov.cn/e/space/?userid=157564&yqcq.xml?feed_filter=20160910Tl3Xa.html
http://www.yqcq.gov.cn/e/space/?userid=157567&yqcq.xml?feed_filter=20160910Iw7Vf.html
http://www.yqcq.gov.cn/e/space/?userid=157569&yqcq.xml?feed_filter=20160910Tq6Mk.html
http://www.yqcq.gov.cn/e/space/?userid=157571&yqcq.xml?feed_filter=20160910As1Zy.html
http://www.yqcq.gov.cn/e/space/?userid=157575&yqcq.xml?feed_filter=20160910Yb8Fw.html
http://www.yqcq.gov.cn/e/space/?userid=157576&yqcq.xml?feed_filter=20160910Jv3Mc.html
http://www.yqcq.gov.cn/e/space/?userid=157580&yqcq.xml?feed_filter=20160910Tp5Ps.html
http://www.yqcq.gov.cn/e/space/?userid=157584&yqcq.xml?feed_filter=20160910Vu6Tk.html
http://www.yqcq.gov.cn/e/space/?userid=157585&yqcq.xml?feed_filter=20160910Ga4Ns.html
http://www.yqcq.gov.cn/e/space/?userid=157587&yqcq.xml?feed_filter=20160910Wh4Wh.html
http://www.yqcq.gov.cn/e/space/?userid=157588&yqcq.xml?feed_filter=20160910Wm9Ok.html
http://www.yqcq.gov.cn/e/space/?userid=157590&yqcq.xml?feed_filter=20160910Mw1Gn.html
http://www.yqcq.gov.cn/e/space/?userid=157591&yqcq.xml?feed_filter=20160910Jj8Ti.html
http://www.yqcq.gov.cn/e/space/?userid=157593&yqcq.xml?feed_filter=20160910Fv1Lg.html
http://www.yqcq.gov.cn/e/space/?userid=157594&yqcq.xml?feed_filter=20160910Fl8Cb.html
http://www.yqcq.gov.cn/e/space/?userid=157596&yqcq.xml?feed_filter=20160910Ni7Jx.html
http://www.yqcq.gov.cn/e/space/?userid=157598&yqcq.xml?feed_filter=20160910Gl9Am.html
http://www.yqcq.gov.cn/e/space/?userid=157599&yqcq.xml?feed_filter=20160910Ci8Xc.html
http://www.yqcq.gov.cn/e/space/?userid=157601&yqcq.xml?feed_filter=20160910Xp2Rm.html
http://www.yqcq.gov.cn/e/space/?userid=157602&yqcq.xml?feed_filter=20160910Wd4Ml.html
http://www.yqcq.gov.cn/e/space/?userid=157603&yqcq.xml?feed_filter=20160910Ig3Yp.html
http://www.yqcq.gov.cn/e/space/?userid=157605&yqcq.xml?feed_filter=20160910Yj7Kq.html
http://www.yqcq.gov.cn/e/space/?userid=157606&yqcq.xml?feed_filter=20160910Zj2Bd.html
http://www.yqcq.gov.cn/e/space/?userid=157608&yqcq.xml?feed_filter=20160910Vq7Ds.html
http://www.yqcq.gov.cn/e/space/?userid=157609&yqcq.xml?feed_filter=20160910Lu4Hj.html
http://www.yqcq.gov.cn/e/space/?userid=157610&yqcq.xml?feed_filter=20160910Su3Wp.html
http://www.yqcq.gov.cn/e/space/?userid=157612&yqcq.xml?feed_filter=20160910Vd3Jo.html
http://www.yqcq.gov.cn/e/space/?userid=157613&yqcq.xml?feed_filter=20160910Tb1Dm.html
http://www.yqcq.gov.cn/e/space/?userid=157614&yqcq.xml?feed_filter=20160910Jm3Az.html
http://www.yqcq.gov.cn/e/space/?userid=157616&yqcq.xml?feed_filter=20160910Ux9Ng.html
http://www.yqcq.gov.cn/e/space/?userid=157617&yqcq.xml?feed_filter=20160910Gt9Jy.html
http://www.yqcq.gov.cn/e/space/?userid=157622&yqcq.xml?feed_filter=20160910Uu2Qc.html
http://www.yqcq.gov.cn/e/space/?userid=157624&yqcq.xml?feed_filter=20160910Jz5Gt.html
http://www.yqcq.gov.cn/e/space/?userid=157627&yqcq.xml?feed_filter=20160910Oe9Qg.html
http://www.yqcq.gov.cn/e/space/?userid=157630&yqcq.xml?feed_filter=20160910Gx7Wc.html
http://www.yqcq.gov.cn/e/space/?userid=157631&yqcq.xml?feed_filter=20160910Jt6Vy.html
http://www.yqcq.gov.cn/e/space/?userid=157633&yqcq.xml?feed_filter=20160910Dz8Nn.html
http://www.yqcq.gov.cn/e/space/?userid=157634&yqcq.xml?feed_filter=20160910Bq3Je.html
http://www.yqcq.gov.cn/e/space/?userid=157636&yqcq.xml?feed_filter=20160910Ze8Pe.html
http://www.yqcq.gov.cn/e/space/?userid=157637&yqcq.xml?feed_filter=20160910Qj7Ds.html
http://www.yqcq.gov.cn/e/space/?userid=157639&yqcq.xml?feed_filter=20160910Zm8Jq.html
http://www.yqcq.gov.cn/e/space/?userid=157641&yqcq.xml?feed_filter=20160910Ia8Si.html
http://www.yqcq.gov.cn/e/space/?userid=157643&yqcq.xml?feed_filter=20160910Un8Ss.html
http://www.yqcq.gov.cn/e/space/?userid=157644&yqcq.xml?feed_filter=20160910Rd2Kn.html
http://www.yqcq.gov.cn/e/space/?userid=157646&yqcq.xml?feed_filter=20160910Hf4Rh.html
http://www.yqcq.gov.cn/e/space/?userid=157647&yqcq.xml?feed_filter=20160910Js5Ma.html
http://www.yqcq.gov.cn/e/space/?userid=157649&yqcq.xml?feed_filter=20160910Uu3Pf.html
http://www.yqcq.gov.cn/e/space/?userid=157650&yqcq.xml?feed_filter=20160910Zw8Ca.html
http://www.yqcq.gov.cn/e/space/?userid=157652&yqcq.xml?feed_filter=20160910Pd9Yl.html
http://www.yqcq.gov.cn/e/space/?userid=157653&yqcq.xml?feed_filter=20160910Wu9Ax.html
http://www.yqcq.gov.cn/e/space/?userid=157654&yqcq.xml?feed_filter=20160910Rs5Km.html
http://www.yqcq.gov.cn/e/space/?userid=157656&yqcq.xml?feed_filter=20160910Za0Cp.html
http://www.yqcq.gov.cn/e/space/?userid=157657&yqcq.xml?feed_filter=20160910Ji5Ty.html
http://www.yqcq.gov.cn/e/space/?userid=157658&yqcq.xml?feed_filter=20160910Yz9Cf.html
http://www.yqcq.gov.cn/e/space/?userid=157660&yqcq.xml?feed_filter=20160910Pu9Gj.html
http://www.yqcq.gov.cn/e/space/?userid=157661&yqcq.xml?feed_filter=20160910Mt2Dq.html
http://www.yqcq.gov.cn/e/space/?userid=157663&yqcq.xml?feed_filter=20160910Uc2Du.html
http://www.yqcq.gov.cn/e/space/?userid=157664&yqcq.xml?feed_filter=20160910Ns4Lr.html
http://www.yqcq.gov.cn/e/space/?userid=157666&yqcq.xml?feed_filter=20160910Xs0Gs.html
http://www.yqcq.gov.cn/e/space/?userid=157667&yqcq.xml?feed_filter=20160910Wo2Sx.html
http://www.yqcq.gov.cn/e/space/?userid=157668&yqcq.xml?feed_filter=20160910Iw7Vd.html
http://www.yqcq.gov.cn/e/space/?userid=157669&yqcq.xml?feed_filter=20160910Ch3Uu.html
http://www.yqcq.gov.cn/e/space/?userid=157671&yqcq.xml?feed_filter=20160910Ki2Va.html
http://www.yqcq.gov.cn/e/space/?userid=157672&yqcq.xml?feed_filter=20160910Rf3Kq.html
http://www.yqcq.gov.cn/e/space/?userid=157674&yqcq.xml?feed_filter=20160910Wp7Ws.html
http://www.yqcq.gov.cn/e/space/?userid=157676&yqcq.xml?feed_filter=20160910Yp2Vy.html
http://www.yqcq.gov.cn/e/space/?userid=157678&yqcq.xml?feed_filter=20160910Kq2Bm.html
http://www.yqcq.gov.cn/e/space/?userid=157679&yqcq.xml?feed_filter=20160910Ph5Gj.html
http://www.yqcq.gov.cn/e/space/?userid=157681&yqcq.xml?feed_filter=20160910Vr6Oi.html
http://www.yqcq.gov.cn/e/space/?userid=157684&yqcq.xml?feed_filter=20160910Le0Sj.html
http://www.yqcq.gov.cn/e/space/?userid=157686&yqcq.xml?feed_filter=20160910Uf0Co.html
http://www.yqcq.gov.cn/e/space/?userid=157690&yqcq.xml?feed_filter=20160910Fd9Vr.html
http://www.yqcq.gov.cn/e/space/?userid=157692&yqcq.xml?feed_filter=20160910Tk6Ip.html
http://www.yqcq.gov.cn/e/space/?userid=157693&yqcq.xml?feed_filter=20160910Ho7Bu.html
http://www.yqcq.gov.cn/e/space/?userid=157695&yqcq.xml?feed_filter=20160910Us4Tc.html
http://www.yqcq.gov.cn/e/space/?userid=157696&yqcq.xml?feed_filter=20160910Ez4Nk.html
http://www.yqcq.gov.cn/e/space/?userid=157697&yqcq.xml?feed_filter=20160910Kf8Cu.html
http://www.yqcq.gov.cn/e/space/?userid=157699&yqcq.xml?feed_filter=20160910Pl9Tj.html
http://www.yqcq.gov.cn/e/space/?userid=157700&yqcq.xml?feed_filter=20160910Qz8Sz.html
http://www.yqcq.gov.cn/e/space/?userid=157701&yqcq.xml?feed_filter=20160910Ap4Gu.html
http://www.yqcq.gov.cn/e/space/?userid=157702&yqcq.xml?feed_filter=20160910Jt4Ae.html
http://www.yqcq.gov.cn/e/space/?userid=157704&yqcq.xml?feed_filter=20160910Yf5Je.html
http://www.yqcq.gov.cn/e/space/?userid=157705&yqcq.xml?feed_filter=20160910Zl4Ei.html
http://www.yqcq.gov.cn/e/space/?userid=157707&yqcq.xml?feed_filter=20160910Mo5Ta.html
http://www.yqcq.gov.cn/e/space/?userid=157708&yqcq.xml?feed_filter=20160910As7Jp.html
http://www.yqcq.gov.cn/e/space/?userid=157710&yqcq.xml?feed_filter=20160910Ug4Lv.html
http://www.yqcq.gov.cn/e/space/?userid=157711&yqcq.xml?feed_filter=20160910In0Wz.html
http://www.yqcq.gov.cn/e/space/?userid=157712&yqcq.xml?feed_filter=20160910Sf4Pj.html
http://www.yqcq.gov.cn/e/space/?userid=157714&yqcq.xml?feed_filter=20160910Zk0Oj.html
http://www.yqcq.gov.cn/e/space/?userid=157715&yqcq.xml?feed_filter=20160910Lr2Io.html
http://www.yqcq.gov.cn/e/space/?userid=157717&yqcq.xml?feed_filter=20160910Ph7Oc.html
http://www.yqcq.gov.cn/e/space/?userid=157718&yqcq.xml?feed_filter=20160910Uu5Mp.html
http://www.yqcq.gov.cn/e/space/?userid=157719&yqcq.xml?feed_filter=20160910Ay3Xs.html
http://www.yqcq.gov.cn/e/space/?userid=157722&yqcq.xml?feed_filter=20160910Ac1Kj.html
http://www.yqcq.gov.cn/e/space/?userid=157723&yqcq.xml?feed_filter=20160910Sp3Ag.html
http://www.yqcq.gov.cn/e/space/?userid=157725&yqcq.xml?feed_filter=20160910Yb4Aa.html
http://www.yqcq.gov.cn/e/space/?userid=157726&yqcq.xml?feed_filter=20160910Hh8Up.html
http://www.yqcq.gov.cn/e/space/?userid=157727&yqcq.xml?feed_filter=20160910Ub6Bx.html
http://www.yqcq.gov.cn/e/space/?userid=157733&yqcq.xml?feed_filter=20160910Gl1Cn.html
http://www.yqcq.gov.cn/e/space/?userid=157734&yqcq.xml?feed_filter=20160910Cx9Yv.html
http://www.yqcq.gov.cn/e/space/?userid=157736&yqcq.xml?feed_filter=20160910Gd8Ox.html
http://www.yqcq.gov.cn/e/space/?userid=157738&yqcq.xml?feed_filter=20160910Nn6Dk.html
http://www.yqcq.gov.cn/e/space/?userid=157741&yqcq.xml?feed_filter=20160910Us1Vm.html
http://www.yqcq.gov.cn/e/space/?userid=157743&yqcq.xml?feed_filter=20160910Gi2Vx.html
http://www.yqcq.gov.cn/e/space/?userid=157744&yqcq.xml?feed_filter=20160910Me6Yo.html
http://www.yqcq.gov.cn/e/space/?userid=157746&yqcq.xml?feed_filter=20160910Nz9Op.html
http://www.yqcq.gov.cn/e/space/?userid=157747&yqcq.xml?feed_filter=20160910Ol5Sg.html
http://www.yqcq.gov.cn/e/space/?userid=157748&yqcq.xml?feed_filter=20160910Ri3Rs.html
http://www.yqcq.gov.cn/e/space/?userid=157749&yqcq.xml?feed_filter=20160910Jl0Gv.html
http://www.yqcq.gov.cn/e/space/?userid=157751&yqcq.xml?feed_filter=20160910Pj4Ez.html
http://www.yqcq.gov.cn/e/space/?userid=157752&yqcq.xml?feed_filter=20160910Md5Mb.html
http://www.yqcq.gov.cn/e/space/?userid=157753&yqcq.xml?feed_filter=20160910Pp3Up.html
http://www.yqcq.gov.cn/e/space/?userid=157757&yqcq.xml?feed_filter=20160910Wp6Pz.html
http://www.yqcq.gov.cn/e/space/?userid=157758&yqcq.xml?feed_filter=20160910Iv9Qq.html
http://www.yqcq.gov.cn/e/space/?userid=157759&yqcq.xml?feed_filter=20160910Ek3Xz.html
http://www.yqcq.gov.cn/e/space/?userid=157760&yqcq.xml?feed_filter=20160910Tz0Fq.html
http://www.yqcq.gov.cn/e/space/?userid=157762&yqcq.xml?feed_filter=20160910Aa2Vw.html
http://www.yqcq.gov.cn/e/space/?userid=157763&yqcq.xml?feed_filter=20160910Ec2Kk.html
http://www.yqcq.gov.cn/e/space/?userid=157764&yqcq.xml?feed_filter=20160910Ko5Dz.html
http://www.yqcq.gov.cn/e/space/?userid=157765&yqcq.xml?feed_filter=20160910Py1Nv.html
http://www.yqcq.gov.cn/e/space/?userid=157767&yqcq.xml?feed_filter=20160910Bs6Wu.html
http://www.yqcq.gov.cn/e/space/?userid=157768&yqcq.xml?feed_filter=20160910Tx0Ns.html
http://www.yqcq.gov.cn/e/space/?userid=157769&yqcq.xml?feed_filter=20160910Yo6Pc.html
http://www.yqcq.gov.cn/e/space/?userid=157771&yqcq.xml?feed_filter=20160910Xr1Ch.html
http://www.yqcq.gov.cn/e/space/?userid=157773&yqcq.xml?feed_filter=20160910Bk4Fh.html
http://www.yqcq.gov.cn/e/space/?userid=157774&yqcq.xml?feed_filter=20160910Wg6Bt.html
http://www.yqcq.gov.cn/e/space/?userid=157775&yqcq.xml?feed_filter=20160910Ng0Jy.html
http://www.yqcq.gov.cn/e/space/?userid=157777&yqcq.xml?feed_filter=20160910Wh4Wz.html
http://www.yqcq.gov.cn/e/space/?userid=157779&yqcq.xml?feed_filter=20160910Yb0Bk.html
http://www.yqcq.gov.cn/e/space/?userid=157780&yqcq.xml?feed_filter=20160910Uq3Kf.html
http://www.yqcq.gov.cn/e/space/?userid=157781&yqcq.xml?feed_filter=20160910Nj1Qp.html
http://www.yqcq.gov.cn/e/space/?userid=157783&yqcq.xml?feed_filter=20160910Ng8Os.html
http://www.yqcq.gov.cn/e/space/?userid=157784&yqcq.xml?feed_filter=20160910Vb7Gg.html
http://www.yqcq.gov.cn/e/space/?userid=157786&yqcq.xml?feed_filter=20160910Pz0Ai.html
http://www.yqcq.gov.cn/e/space/?userid=157788&yqcq.xml?feed_filter=20160910Sj4Li.html
http://www.yqcq.gov.cn/e/space/?userid=157790&yqcq.xml?feed_filter=20160910Bs8Lk.html
http://www.yqcq.gov.cn/e/space/?userid=157791&yqcq.xml?feed_filter=20160910Xk8Qn.html
http://www.yqcq.gov.cn/e/space/?userid=157792&yqcq.xml?feed_filter=20160910Zv6Fu.html
http://www.yqcq.gov.cn/e/space/?userid=157793&yqcq.xml?feed_filter=20160910Vi4Yw.html
http://www.yqcq.gov.cn/e/space/?userid=157796&yqcq.xml?feed_filter=20160910Mw8Vf.html
http://www.yqcq.gov.cn/e/space/?userid=157799&yqcq.xml?feed_filter=20160910Pn1Mk.html
http://www.yqcq.gov.cn/e/space/?userid=157800&yqcq.xml?feed_filter=20160910Je0De.html
http://www.yqcq.gov.cn/e/space/?userid=157802&yqcq.xml?feed_filter=20160910Zc3Vl.html
http://www.yqcq.gov.cn/e/space/?userid=157805&yqcq.xml?feed_filter=20160910Au4At.html
http://www.yqcq.gov.cn/e/space/?userid=157807&yqcq.xml?feed_filter=20160910Dj2Pw.html
http://www.yqcq.gov.cn/e/space/?userid=157809&yqcq.xml?feed_filter=20160910Zc0Dv.html
http://www.yqcq.gov.cn/e/space/?userid=157810&yqcq.xml?feed_filter=20160910Ez0Qn.html
http://www.yqcq.gov.cn/e/space/?userid=157811&yqcq.xml?feed_filter=20160910Jb6Tn.html
http://www.yqcq.gov.cn/e/space/?userid=157813&yqcq.xml?feed_filter=20160910Hy0Wt.html
http://www.yqcq.gov.cn/e/space/?userid=157814&yqcq.xml?feed_filter=20160910Sp5Zs.html
http://www.yqcq.gov.cn/e/space/?userid=157815&yqcq.xml?feed_filter=20160910Ox6Cb.html
http://www.yqcq.gov.cn/e/space/?userid=157818&yqcq.xml?feed_filter=20160910Ca4Ou.html
http://www.yqcq.gov.cn/e/space/?userid=157819&yqcq.xml?feed_filter=20160910Yi8Tj.html
http://www.yqcq.gov.cn/e/space/?userid=157820&yqcq.xml?feed_filter=20160910Te9Rb.html
http://www.yqcq.gov.cn/e/space/?userid=157822&yqcq.xml?feed_filter=20160910Ev7Ss.html
http://www.yqcq.gov.cn/e/space/?userid=157823&yqcq.xml?feed_filter=20160910Wh0Oi.html
http://www.yqcq.gov.cn/e/space/?userid=157824&yqcq.xml?feed_filter=20160910Mw8Ey.html
http://www.yqcq.gov.cn/e/space/?userid=157826&yqcq.xml?feed_filter=20160910Qd6Kw.html
http://www.yqcq.gov.cn/e/space/?userid=157827&yqcq.xml?feed_filter=20160910Dh5Nu.html
http://www.yqcq.gov.cn/e/space/?userid=157828&yqcq.xml?feed_filter=20160910Fw3Yl.html
http://www.yqcq.gov.cn/e/space/?userid=157830&yqcq.xml?feed_filter=20160910Gf4Pd.html
http://www.yqcq.gov.cn/e/space/?userid=157832&yqcq.xml?feed_filter=20160910Fy9Du.html
http://www.yqcq.gov.cn/e/space/?userid=157833&yqcq.xml?feed_filter=20160910Ts6Zj.html
http://www.yqcq.gov.cn/e/space/?userid=157834&yqcq.xml?feed_filter=20160910Wk3Uq.html
http://www.yqcq.gov.cn/e/space/?userid=157836&yqcq.xml?feed_filter=20160910Xt3Zt.html
http://www.yqcq.gov.cn/e/space/?userid=157837&yqcq.xml?feed_filter=20160910Jy1Ij.html
http://www.yqcq.gov.cn/e/space/?userid=157839&yqcq.xml?feed_filter=20160910Wm5Os.html
http://www.yqcq.gov.cn/e/space/?userid=157841&yqcq.xml?feed_filter=20160910If3Ie.html
http://www.yqcq.gov.cn/e/space/?userid=157842&yqcq.xml?feed_filter=20160910Rm4Lm.html
http://www.yqcq.gov.cn/e/space/?userid=157843&yqcq.xml?feed_filter=20160910Zg8Is.html
http://www.yqcq.gov.cn/e/space/?userid=157844&yqcq.xml?feed_filter=20160910Vb7Jo.html
http://www.yqcq.gov.cn/e/space/?userid=157847&yqcq.xml?feed_filter=20160910Zx2Zn.html
http://www.yqcq.gov.cn/e/space/?userid=157850&yqcq.xml?feed_filter=20160910Ad1Fn.html
http://www.yqcq.gov.cn/e/space/?userid=157853&yqcq.xml?feed_filter=20160910Ee6Qi.html
http://www.yqcq.gov.cn/e/space/?userid=157854&yqcq.xml?feed_filter=20160910Dh6Uv.html
http://www.yqcq.gov.cn/e/space/?userid=157857&yqcq.xml?feed_filter=20160910Ro2Qq.html
http://www.yqcq.gov.cn/e/space/?userid=157858&yqcq.xml?feed_filter=20160910Mr4Tv.html
http://www.yqcq.gov.cn/e/space/?userid=157860&yqcq.xml?feed_filter=20160910Hp8Ef.html
http://www.yqcq.gov.cn/e/space/?userid=157861&yqcq.xml?feed_filter=20160910Sm7Sp.html
http://www.yqcq.gov.cn/e/space/?userid=157862&yqcq.xml?feed_filter=20160910Ua3Jh.html
http://www.yqcq.gov.cn/e/space/?userid=157864&yqcq.xml?feed_filter=20160910Ee8Sg.html
http://www.yqcq.gov.cn/e/space/?userid=157866&yqcq.xml?feed_filter=20160910Tj9Mh.html
http://www.yqcq.gov.cn/e/space/?userid=157867&yqcq.xml?feed_filter=20160910Vw1Mv.html
http://www.yqcq.gov.cn/e/space/?userid=157868&yqcq.xml?feed_filter=20160910Fb6Km.html
http://www.yqcq.gov.cn/e/space/?userid=157871&yqcq.xml?feed_filter=20160910Zg0Du.html
http://www.yqcq.gov.cn/e/space/?userid=157872&yqcq.xml?feed_filter=20160910Nc7Ez.html
http://www.yqcq.gov.cn/e/space/?userid=157874&yqcq.xml?feed_filter=20160910Au5Gg.html
http://www.yqcq.gov.cn/e/space/?userid=157876&yqcq.xml?feed_filter=20160910Hw0Ei.html
http://www.yqcq.gov.cn/e/space/?userid=157877&yqcq.xml?feed_filter=20160910Ia8Ap.html
http://www.yqcq.gov.cn/e/space/?userid=157878&yqcq.xml?feed_filter=20160910Hj3Lb.html
http://www.yqcq.gov.cn/e/space/?userid=157880&yqcq.xml?feed_filter=20160910Fk6Cc.html
http://www.yqcq.gov.cn/e/space/?userid=157881&yqcq.xml?feed_filter=20160910Oo1Wu.html
http://www.yqcq.gov.cn/e/space/?userid=157882&yqcq.xml?feed_filter=20160910Tl8Lc.html
http://www.yqcq.gov.cn/e/space/?userid=157884&yqcq.xml?feed_filter=20160910Dr9Gz.html
http://www.yqcq.gov.cn/e/space/?userid=157885&yqcq.xml?feed_filter=20160910Rl5Md.html
http://www.yqcq.gov.cn/e/space/?userid=157886&yqcq.xml?feed_filter=20160910Lh3Gq.html
http://www.yqcq.gov.cn/e/space/?userid=157888&yqcq.xml?feed_filter=20160910Sx7Ja.html
http://www.yqcq.gov.cn/e/space/?userid=157889&yqcq.xml?feed_filter=20160910Ur1Tz.html
http://www.yqcq.gov.cn/e/space/?userid=157891&yqcq.xml?feed_filter=20160910Pb6Fq.html
http://www.yqcq.gov.cn/e/space/?userid=157894&yqcq.xml?feed_filter=20160910Af0Wo.html
http://www.yqcq.gov.cn/e/space/?userid=157896&yqcq.xml?feed_filter=20160910Cs2Xt.html
http://www.yqcq.gov.cn/e/space/?userid=157898&yqcq.xml?feed_filter=20160910Fc2Hr.html
http://www.yqcq.gov.cn/e/space/?userid=157899&yqcq.xml?feed_filter=20160910Pq8Sa.html
http://www.yqcq.gov.cn/e/space/?userid=157903&yqcq.xml?feed_filter=20160910Tv3Vi.html
http://www.yqcq.gov.cn/e/space/?userid=157904&yqcq.xml?feed_filter=20160910Hp1Ze.html
http://www.yqcq.gov.cn/e/space/?userid=157905&yqcq.xml?feed_filter=20160910Mt5Yr.html
http://www.yqcq.gov.cn/e/space/?userid=157908&yqcq.xml?feed_filter=20160910Xs9Kv.html
http://www.yqcq.gov.cn/e/space/?userid=157909&yqcq.xml?feed_filter=20160910Ef3Ie.html
http://www.yqcq.gov.cn/e/space/?userid=157910&yqcq.xml?feed_filter=20160910Yx0Kv.html
http://www.yqcq.gov.cn/e/space/?userid=157911&yqcq.xml?feed_filter=20160910Ph2Ca.html
http://www.yqcq.gov.cn/e/space/?userid=157913&yqcq.xml?feed_filter=20160910Vx0Tn.html
http://www.yqcq.gov.cn/e/space/?userid=157915&yqcq.xml?feed_filter=20160910Py9Tq.html
http://www.yqcq.gov.cn/e/space/?userid=157917&yqcq.xml?feed_filter=20160910Si8Si.html
http://www.yqcq.gov.cn/e/space/?userid=157918&yqcq.xml?feed_filter=20160910Zu7Pp.html
http://www.yqcq.gov.cn/e/space/?userid=157919&yqcq.xml?feed_filter=20160910Ld1Nr.html
http://www.yqcq.gov.cn/e/space/?userid=157920&yqcq.xml?feed_filter=20160910Qt3Sz.html
http://www.yqcq.gov.cn/e/space/?userid=157921&yqcq.xml?feed_filter=20160910Fe7Lj.html
http://www.yqcq.gov.cn/e/space/?userid=157923&yqcq.xml?feed_filter=20160910Zj4Zk.html
http://www.yqcq.gov.cn/e/space/?userid=157924&yqcq.xml?feed_filter=20160910Nb8Ns.html
http://www.yqcq.gov.cn/e/space/?userid=157926&yqcq.xml?feed_filter=20160910Oe5Qr.html
http://www.yqcq.gov.cn/e/space/?userid=157927&yqcq.xml?feed_filter=20160910No0Ui.html
http://www.yqcq.gov.cn/e/space/?userid=157928&yqcq.xml?feed_filter=20160910Pi3Wj.html
http://www.yqcq.gov.cn/e/space/?userid=157930&yqcq.xml?feed_filter=20160910Mf5Lo.html
http://www.yqcq.gov.cn/e/space/?userid=157931&yqcq.xml?feed_filter=20160910Zp6Aq.html
http://www.yqcq.gov.cn/e/space/?userid=157933&yqcq.xml?feed_filter=20160910Et0Yh.html
http://www.yqcq.gov.cn/e/space/?userid=157934&yqcq.xml?feed_filter=20160910Fd2Dn.html
http://www.yqcq.gov.cn/e/space/?userid=157936&yqcq.xml?feed_filter=20160910Iq8Wp.html
http://www.yqcq.gov.cn/e/space/?userid=157938&yqcq.xml?feed_filter=20160910Fr6Qt.html
http://www.yqcq.gov.cn/e/space/?userid=157941&yqcq.xml?feed_filter=20160910Rv7Lt.html
http://www.yqcq.gov.cn/e/space/?userid=157942&yqcq.xml?feed_filter=20160910Gv0Qs.html
http://www.yqcq.gov.cn/e/space/?userid=157945&yqcq.xml?feed_filter=20160910Fc9Tm.html
http://www.yqcq.gov.cn/e/space/?userid=157946&yqcq.xml?feed_filter=20160910Nj8Ax.html
http://www.yqcq.gov.cn/e/space/?userid=157949&yqcq.xml?feed_filter=20160910Nk3Ls.html
http://www.yqcq.gov.cn/e/space/?userid=157950&yqcq.xml?feed_filter=20160910Qv3Kj.html
http://www.yqcq.gov.cn/e/space/?userid=157953&yqcq.xml?feed_filter=20160910Wb3Ag.html
http://www.yqcq.gov.cn/e/space/?userid=157954&yqcq.xml?feed_filter=20160910Op1Zg.html
http://www.yqcq.gov.cn/e/space/?userid=157955&yqcq.xml?feed_filter=20160910Vq1Or.html
http://www.yqcq.gov.cn/e/space/?userid=157957&yqcq.xml?feed_filter=20160910Wv3Vr.html
http://www.yqcq.gov.cn/e/space/?userid=157958&yqcq.xml?feed_filter=20160910Sr6Hv.html
http://www.yqcq.gov.cn/e/space/?userid=157959&yqcq.xml?feed_filter=20160910Wl7Sk.html
http://www.yqcq.gov.cn/e/space/?userid=157962&yqcq.xml?feed_filter=20160910Lj4Ey.html
http://www.yqcq.gov.cn/e/space/?userid=157964&yqcq.xml?feed_filter=20160910Fy5Hi.html
http://www.yqcq.gov.cn/e/space/?userid=157966&yqcq.xml?feed_filter=20160910Tg3Vh.html
http://www.yqcq.gov.cn/e/space/?userid=157967&yqcq.xml?feed_filter=20160910El4Xw.html
http://www.yqcq.gov.cn/e/space/?userid=157969&yqcq.xml?feed_filter=20160910Nd0Ht.html
http://www.yqcq.gov.cn/e/space/?userid=157970&yqcq.xml?feed_filter=20160910Tm8Io.html
http://www.yqcq.gov.cn/e/space/?userid=157971&yqcq.xml?feed_filter=20160910Ds4Yp.html
http://www.yqcq.gov.cn/e/space/?userid=157972&yqcq.xml?feed_filter=20160910Zk4Ex.html
http://www.yqcq.gov.cn/e/space/?userid=157974&yqcq.xml?feed_filter=20160910Yc5Ic.html
http://www.yqcq.gov.cn/e/space/?userid=157975&yqcq.xml?feed_filter=20160910Up0Uc.html
http://www.yqcq.gov.cn/e/space/?userid=157976&yqcq.xml?feed_filter=20160910Xa1Wu.html
http://www.yqcq.gov.cn/e/space/?userid=157977&yqcq.xml?feed_filter=20160910Rd0Gh.html
http://www.yqcq.gov.cn/e/space/?userid=157979&yqcq.xml?feed_filter=20160910Kv8Fb.html
http://www.yqcq.gov.cn/e/space/?userid=157980&yqcq.xml?feed_filter=20160910Vy1Hk.html
http://www.yqcq.gov.cn/e/space/?userid=157981&yqcq.xml?feed_filter=20160910Wk1Hm.html
http://www.yqcq.gov.cn/e/space/?userid=157982&yqcq.xml?feed_filter=20160910Kt1Rb.html
http://www.yqcq.gov.cn/e/space/?userid=157984&yqcq.xml?feed_filter=20160910Gd4Kk.html
http://www.yqcq.gov.cn/e/space/?userid=157985&yqcq.xml?feed_filter=20160910Ls6Kq.html
http://www.yqcq.gov.cn/e/space/?userid=157987&yqcq.xml?feed_filter=20160910Qx3Jt.html
http://www.yqcq.gov.cn/e/space/?userid=157990&yqcq.xml?feed_filter=20160910Yc6Yf.html
http://www.yqcq.gov.cn/e/space/?userid=157992&yqcq.xml?feed_filter=20160910Do3Oy.html
http://www.yqcq.gov.cn/e/space/?userid=157995&yqcq.xml?feed_filter=20160910Sm6Hq.html
http://www.yqcq.gov.cn/e/space/?userid=157996&yqcq.xml?feed_filter=20160910Bp8Mw.html
http://www.yqcq.gov.cn/e/space/?userid=157998&yqcq.xml?feed_filter=20160910My9En.html
http://www.yqcq.gov.cn/e/space/?userid=157999&yqcq.xml?feed_filter=20160910Zy7Kz.html
http://www.yqcq.gov.cn/e/space/?userid=158000&yqcq.xml?feed_filter=20160910Qk9Yk.html
http://www.yqcq.gov.cn/e/space/?userid=158002&yqcq.xml?feed_filter=20160910Wq6Ng.html
http://www.yqcq.gov.cn/e/space/?userid=158004&yqcq.xml?feed_filter=20160910Jw8Vi.html
http://www.yqcq.gov.cn/e/space/?userid=158006&yqcq.xml?feed_filter=20160910We9Wk.html
http://www.yqcq.gov.cn/e/space/?userid=158008&yqcq.xml?feed_filter=20160910Am2Ow.html
http://www.yqcq.gov.cn/e/space/?userid=158009&yqcq.xml?feed_filter=20160910Uw5Ul.html
http://www.yqcq.gov.cn/e/space/?userid=158012&yqcq.xml?feed_filter=20160910Lw4Tj.html
http://www.yqcq.gov.cn/e/space/?userid=158015&yqcq.xml?feed_filter=20160910St2Kv.html
http://www.yqcq.gov.cn/e/space/?userid=158016&yqcq.xml?feed_filter=20160910Lm3Kb.html
http://www.yqcq.gov.cn/e/space/?userid=158017&yqcq.xml?feed_filter=20160910Nn3Wx.html
http://www.yqcq.gov.cn/e/space/?userid=158018&yqcq.xml?feed_filter=20160910Dp9Cj.html
http://www.yqcq.gov.cn/e/space/?userid=158020&yqcq.xml?feed_filter=20160910Qn4Ru.html
http://www.yqcq.gov.cn/e/space/?userid=158021&yqcq.xml?feed_filter=20160910Jd2Yv.html
http://www.yqcq.gov.cn/e/space/?userid=158022&yqcq.xml?feed_filter=20160910Gx5Cf.html
http://www.yqcq.gov.cn/e/space/?userid=158023&yqcq.xml?feed_filter=20160910Ps4Kq.html
http://www.yqcq.gov.cn/e/space/?userid=158025&yqcq.xml?feed_filter=20160910Vi9Kz.html
http://www.yqcq.gov.cn/e/space/?userid=158026&yqcq.xml?feed_filter=20160910Sw6Ph.html
http://www.yqcq.gov.cn/e/space/?userid=158027&yqcq.xml?feed_filter=20160910Xr4Qm.html
http://www.yqcq.gov.cn/e/space/?userid=158028&yqcq.xml?feed_filter=20160910Fd8Jy.html
http://www.yqcq.gov.cn/e/space/?userid=158030&yqcq.xml?feed_filter=20160910Kt0Ne.html
http://www.yqcq.gov.cn/e/space/?userid=158031&yqcq.xml?feed_filter=20160910Zr4Kg.html
http://www.yqcq.gov.cn/e/space/?userid=158032&yqcq.xml?feed_filter=20160910Sz4Oo.html
http://www.yqcq.gov.cn/e/space/?userid=158033&yqcq.xml?feed_filter=20160910Fg5Ph.html
http://www.yqcq.gov.cn/e/space/?userid=158035&yqcq.xml?feed_filter=20160910Np0El.html
http://www.yqcq.gov.cn/e/space/?userid=158036&yqcq.xml?feed_filter=20160910Li2Bc.html
http://www.yqcq.gov.cn/e/space/?userid=158037&yqcq.xml?feed_filter=20160910Qg2Bp.html
http://www.yqcq.gov.cn/e/space/?userid=158040&yqcq.xml?feed_filter=20160910Xi1Du.html
http://www.yqcq.gov.cn/e/space/?userid=158043&yqcq.xml?feed_filter=20160910As7Ix.html
http://www.yqcq.gov.cn/e/space/?userid=158044&yqcq.xml?feed_filter=20160910Wo0Sb.html
http://www.yqcq.gov.cn/e/space/?userid=158045&yqcq.xml?feed_filter=20160910Eg9Te.html
http://www.yqcq.gov.cn/e/space/?userid=158047&yqcq.xml?feed_filter=20160910Fk1Yc.html
http://www.yqcq.gov.cn/e/space/?userid=158048&yqcq.xml?feed_filter=20160910Kq5Sg.html
http://www.yqcq.gov.cn/e/space/?userid=158050&yqcq.xml?feed_filter=20160910Wc8Rw.html
http://www.yqcq.gov.cn/e/space/?userid=158051&yqcq.xml?feed_filter=20160910Qt3Ga.html
http://www.yqcq.gov.cn/e/space/?userid=158054&yqcq.xml?feed_filter=20160910Mi1Qp.html
http://www.yqcq.gov.cn/e/space/?userid=158056&yqcq.xml?feed_filter=20160910Do7Gr.html
http://www.yqcq.gov.cn/e/space/?userid=158057&yqcq.xml?feed_filter=20160910Yq2Dr.html
http://www.yqcq.gov.cn/e/space/?userid=158059&yqcq.xml?feed_filter=20160910Wp6Yb.html
http://www.yqcq.gov.cn/e/space/?userid=158060&yqcq.xml?feed_filter=20160910Oo7Xz.html
http://www.yqcq.gov.cn/e/space/?userid=158061&yqcq.xml?feed_filter=20160910Uj4Vc.html
http://www.yqcq.gov.cn/e/space/?userid=158064&yqcq.xml?feed_filter=20160910Rz8Bh.html
http://www.yqcq.gov.cn/e/space/?userid=158065&yqcq.xml?feed_filter=20160910Ws4Xj.html
http://www.yqcq.gov.cn/e/space/?userid=158066&yqcq.xml?feed_filter=20160910Vr5Kt.html
http://www.yqcq.gov.cn/e/space/?userid=158068&yqcq.xml?feed_filter=20160910Kn8Xl.html
http://www.yqcq.gov.cn/e/space/?userid=158069&yqcq.xml?feed_filter=20160910Db1Xv.html
http://www.yqcq.gov.cn/e/space/?userid=158070&yqcq.xml?feed_filter=20160910Kk8Xx.html
http://www.yqcq.gov.cn/e/space/?userid=158072&yqcq.xml?feed_filter=20160910Ez9Uc.html
http://www.yqcq.gov.cn/e/space/?userid=158073&yqcq.xml?feed_filter=20160910Po1As.html
http://www.yqcq.gov.cn/e/space/?userid=158075&yqcq.xml?feed_filter=20160910Ac1Aa.html
http://www.yqcq.gov.cn/e/space/?userid=158076&yqcq.xml?feed_filter=20160910Oi9Dk.html
http://www.yqcq.gov.cn/e/space/?userid=158078&yqcq.xml?feed_filter=20160910Qu9Ro.html
http://www.yqcq.gov.cn/e/space/?userid=158079&yqcq.xml?feed_filter=20160910Bj6Lr.html
http://www.yqcq.gov.cn/e/space/?userid=158081&yqcq.xml?feed_filter=20160910Tc2Ed.html
http://www.yqcq.gov.cn/e/space/?userid=158082&yqcq.xml?feed_filter=20160910Ky5Pu.html
http://www.yqcq.gov.cn/e/space/?userid=158084&yqcq.xml?feed_filter=20160910Je6Bk.html
http://www.yqcq.gov.cn/e/space/?userid=158086&yqcq.xml?feed_filter=20160910Sl4Hk.html
http://www.yqcq.gov.cn/e/space/?userid=158087&yqcq.xml?feed_filter=20160910Hb9Lv.html
http://www.yqcq.gov.cn/e/space/?userid=158088&yqcq.xml?feed_filter=20160910Jj5Wl.html
http://www.yqcq.gov.cn/e/space/?userid=158089&yqcq.xml?feed_filter=20160910Uh0Hk.html
http://www.yqcq.gov.cn/e/space/?userid=158091&yqcq.xml?feed_filter=20160910Rq5Da.html
http://www.yqcq.gov.cn/e/space/?userid=158092&yqcq.xml?feed_filter=20160910Sl5Pr.html
http://www.yqcq.gov.cn/e/space/?userid=158093&yqcq.xml?feed_filter=20160910Ek9Xa.html
http://www.yqcq.gov.cn/e/space/?userid=158094&yqcq.xml?feed_filter=20160910Kp2Ig.html
http://www.yqcq.gov.cn/e/space/?userid=158096&yqcq.xml?feed_filter=20160910Nu5Kn.html
http://www.yqcq.gov.cn/e/space/?userid=158098&yqcq.xml?feed_filter=20160910Iz2Gr.html
http://www.yqcq.gov.cn/e/space/?userid=158102&yqcq.xml?feed_filter=20160910Fb7Yw.html
http://www.yqcq.gov.cn/e/space/?userid=158106&yqcq.xml?feed_filter=20160910Ph3Mr.html
http://www.yqcq.gov.cn/e/space/?userid=158108&yqcq.xml?feed_filter=20160910Zm3Dl.html
http://www.yqcq.gov.cn/e/space/?userid=158109&yqcq.xml?feed_filter=20160910Qr2Yl.html
http://www.yqcq.gov.cn/e/space/?userid=158111&yqcq.xml?feed_filter=20160910Pw9Rh.html
http://www.yqcq.gov.cn/e/space/?userid=158112&yqcq.xml?feed_filter=20160910Fm3Ta.html
http://www.yqcq.gov.cn/e/space/?userid=158113&yqcq.xml?feed_filter=20160910Xf4Rd.html
http://www.yqcq.gov.cn/e/space/?userid=158114&yqcq.xml?feed_filter=20160910Mr0Yq.html
http://www.yqcq.gov.cn/e/space/?userid=158116&yqcq.xml?feed_filter=20160910An1Hr.html
http://www.yqcq.gov.cn/e/space/?userid=158117&yqcq.xml?feed_filter=20160910Yi0Mr.html
http://www.yqcq.gov.cn/e/space/?userid=158118&yqcq.xml?feed_filter=20160910Ll4Ak.html
http://www.yqcq.gov.cn/e/space/?userid=158121&yqcq.xml?feed_filter=20160910Li1Uu.html
http://www.yqcq.gov.cn/e/space/?userid=158122&yqcq.xml?feed_filter=20160910Qf7Cz.html
http://www.yqcq.gov.cn/e/space/?userid=158124&yqcq.xml?feed_filter=20160910Bp3Ya.html
http://www.yqcq.gov.cn/e/space/?userid=158125&yqcq.xml?feed_filter=20160910Md3Xg.html
http://www.yqcq.gov.cn/e/space/?userid=158126&yqcq.xml?feed_filter=20160910Sj5La.html
http://www.yqcq.gov.cn/e/space/?userid=158128&yqcq.xml?feed_filter=20160910Uz4Sy.html
http://www.yqcq.gov.cn/e/space/?userid=158130&yqcq.xml?feed_filter=20160910Fe2Dn.html
http://www.yqcq.gov.cn/e/space/?userid=158131&yqcq.xml?feed_filter=20160910Kr6Iw.html
http://www.yqcq.gov.cn/e/space/?userid=158133&yqcq.xml?feed_filter=20160910Ke7Jd.html
http://www.yqcq.gov.cn/e/space/?userid=158134&yqcq.xml?feed_filter=20160910Ph2Du.html
http://www.yqcq.gov.cn/e/space/?userid=158136&yqcq.xml?feed_filter=20160910Gd7Bs.html
http://www.yqcq.gov.cn/e/space/?userid=158137&yqcq.xml?feed_filter=20160910Wj9Rp.html
http://www.yqcq.gov.cn/e/space/?userid=158139&yqcq.xml?feed_filter=20160910Wo9Of.html
http://www.yqcq.gov.cn/e/space/?userid=158140&yqcq.xml?feed_filter=20160910Tg0Vz.html
http://www.yqcq.gov.cn/e/space/?userid=158141&yqcq.xml?feed_filter=20160910Pb4Jd.html
http://www.yqcq.gov.cn/e/space/?userid=158143&yqcq.xml?feed_filter=20160910Ni1Px.html
http://www.yqcq.gov.cn/e/space/?userid=158144&yqcq.xml?feed_filter=20160910Nt5Gc.html
http://www.yqcq.gov.cn/e/space/?userid=158145&yqcq.xml?feed_filter=20160910Sz0Gk.html
http://www.yqcq.gov.cn/e/space/?userid=158147&yqcq.xml?feed_filter=20160910Ar5Zj.html
http://www.yqcq.gov.cn/e/space/?userid=158150&yqcq.xml?feed_filter=20160910Zv9Nu.html
http://www.yqcq.gov.cn/e/space/?userid=158151&yqcq.xml?feed_filter=20160910Ar8Hx.html
http://www.yqcq.gov.cn/e/space/?userid=158152&yqcq.xml?feed_filter=20160910Ne6Ne.html
http://www.yqcq.gov.cn/e/space/?userid=158154&yqcq.xml?feed_filter=20160910Rv0Ag.html
http://www.yqcq.gov.cn/e/space/?userid=158158&yqcq.xml?feed_filter=20160910Iy9Bu.html
http://www.yqcq.gov.cn/e/space/?userid=158159&yqcq.xml?feed_filter=20160910Jp3Xk.html
http://www.yqcq.gov.cn/e/space/?userid=158161&yqcq.xml?feed_filter=20160910Zj4An.html
http://www.yqcq.gov.cn/e/space/?userid=158162&yqcq.xml?feed_filter=20160910Kp2Za.html
http://www.yqcq.gov.cn/e/space/?userid=158164&yqcq.xml?feed_filter=20160910Ch7Zo.html
http://www.yqcq.gov.cn/e/space/?userid=158166&yqcq.xml?feed_filter=20160910Qi0Tt.html
http://www.yqcq.gov.cn/e/space/?userid=158167&yqcq.xml?feed_filter=20160910So8Qn.html
http://www.yqcq.gov.cn/e/space/?userid=158169&yqcq.xml?feed_filter=20160910Vy7Qo.html
http://www.yqcq.gov.cn/e/space/?userid=158170&yqcq.xml?feed_filter=20160910Cr2Yh.html
http://www.yqcq.gov.cn/e/space/?userid=158171&yqcq.xml?feed_filter=20160910Om3Pu.html
http://www.yqcq.gov.cn/e/space/?userid=158173&yqcq.xml?feed_filter=20160910Hi2Ad.html
http://www.yqcq.gov.cn/e/space/?userid=158175&yqcq.xml?feed_filter=20160910Om0Ft.html
http://www.yqcq.gov.cn/e/space/?userid=158178&yqcq.xml?feed_filter=20160910Fz1Zh.html
http://www.yqcq.gov.cn/e/space/?userid=158179&yqcq.xml?feed_filter=20160910Up9Dn.html
http://www.yqcq.gov.cn/e/space/?userid=158180&yqcq.xml?feed_filter=20160910Yq1Sc.html
http://www.yqcq.gov.cn/e/space/?userid=158182&yqcq.xml?feed_filter=20160910Yf0Dt.html
http://www.yqcq.gov.cn/e/space/?userid=158183&yqcq.xml?feed_filter=20160910Wr0Cl.html
http://www.yqcq.gov.cn/e/space/?userid=158185&yqcq.xml?feed_filter=20160910Ar7Ow.html
http://www.yqcq.gov.cn/e/space/?userid=158186&yqcq.xml?feed_filter=20160910Xa7Cq.html
http://www.yqcq.gov.cn/e/space/?userid=158188&yqcq.xml?feed_filter=20160910Vn9Pe.html
http://www.yqcq.gov.cn/e/space/?userid=158189&yqcq.xml?feed_filter=20160910Xj3Sa.html
http://www.yqcq.gov.cn/e/space/?userid=158191&yqcq.xml?feed_filter=20160910Ic2Lw.html
http://www.yqcq.gov.cn/e/space/?userid=158192&yqcq.xml?feed_filter=20160910Vf1Rn.html
http://www.yqcq.gov.cn/e/space/?userid=158193&yqcq.xml?feed_filter=20160910Yg5Jf.html
http://www.yqcq.gov.cn/e/space/?userid=158197&yqcq.xml?feed_filter=20160910Um4To.html
http://www.yqcq.gov.cn/e/space/?userid=158199&yqcq.xml?feed_filter=20160910Bo4Qj.html
http://www.yqcq.gov.cn/e/space/?userid=158201&yqcq.xml?feed_filter=20160910Na9Ls.html
http://www.yqcq.gov.cn/e/space/?userid=158204&yqcq.xml?feed_filter=20160910De1Zt.html
http://www.yqcq.gov.cn/e/space/?userid=158206&yqcq.xml?feed_filter=20160910Cz5Rb.html
http://www.yqcq.gov.cn/e/space/?userid=158207&yqcq.xml?feed_filter=20160910Go1Um.html
http://www.yqcq.gov.cn/e/space/?userid=158209&yqcq.xml?feed_filter=20160910Hd1If.html
http://www.yqcq.gov.cn/e/space/?userid=158210&yqcq.xml?feed_filter=20160910Um7Wy.html
http://www.yqcq.gov.cn/e/space/?userid=158212&yqcq.xml?feed_filter=20160910Fg2Lz.html
http://www.yqcq.gov.cn/e/space/?userid=158214&yqcq.xml?feed_filter=20160910Pk3Ka.html
http://www.yqcq.gov.cn/e/space/?userid=158215&yqcq.xml?feed_filter=20160910Zk0Aj.html
http://www.yqcq.gov.cn/e/space/?userid=158217&yqcq.xml?feed_filter=20160910Cz6Pt.html
http://www.yqcq.gov.cn/e/space/?userid=158218&yqcq.xml?feed_filter=20160910Ch5Mt.html
http://www.yqcq.gov.cn/e/space/?userid=158220&yqcq.xml?feed_filter=20160910Uw7Cb.html
http://www.yqcq.gov.cn/e/space/?userid=158222&yqcq.xml?feed_filter=20160910Gn3Zn.html
http://www.yqcq.gov.cn/e/space/?userid=158223&yqcq.xml?feed_filter=20160910Cl3Oq.html
http://www.yqcq.gov.cn/e/space/?userid=158224&yqcq.xml?feed_filter=20160910Cv1Sm.html
http://www.yqcq.gov.cn/e/space/?userid=158225&yqcq.xml?feed_filter=20160910Oz2Sl.html
http://www.yqcq.gov.cn/e/space/?userid=158226&yqcq.xml?feed_filter=20160910Zb9Hr.html
http://www.yqcq.gov.cn/e/space/?userid=158228&yqcq.xml?feed_filter=20160910Rs5Zf.html
http://www.yqcq.gov.cn/e/space/?userid=158229&yqcq.xml?feed_filter=20160910Vv7He.html
http://www.yqcq.gov.cn/e/space/?userid=158230&yqcq.xml?feed_filter=20160910Gw2Wh.html
http://www.yqcq.gov.cn/e/space/?userid=158231&yqcq.xml?feed_filter=20160910Tz8Ld.html
http://www.yqcq.gov.cn/e/space/?userid=158233&yqcq.xml?feed_filter=20160910Vz9Hz.html
http://www.yqcq.gov.cn/e/space/?userid=158234&yqcq.xml?feed_filter=20160910Zb7Us.html
http://www.yqcq.gov.cn/e/space/?userid=158235&yqcq.xml?feed_filter=20160910Gv1Lk.html
http://www.yqcq.gov.cn/e/space/?userid=158236&yqcq.xml?feed_filter=20160910Bd0Vy.html
http://www.yqcq.gov.cn/e/space/?userid=158238&yqcq.xml?feed_filter=20160910Cy6Jx.html
http://www.yqcq.gov.cn/e/space/?userid=158239&yqcq.xml?feed_filter=20160910Et9Sb.html
http://www.yqcq.gov.cn/e/space/?userid=158240&yqcq.xml?feed_filter=20160910Ob4Se.html
http://www.yqcq.gov.cn/e/space/?userid=158243&yqcq.xml?feed_filter=20160910Qy3Qt.html
http://www.yqcq.gov.cn/e/space/?userid=158244&yqcq.xml?feed_filter=20160910Wo9Pk.html
http://www.yqcq.gov.cn/e/space/?userid=158246&yqcq.xml?feed_filter=20160910Nc2Yj.html
http://www.yqcq.gov.cn/e/space/?userid=158249&yqcq.xml?feed_filter=20160910Pu2Vn.html
http://www.yqcq.gov.cn/e/space/?userid=158251&yqcq.xml?feed_filter=20160910Ff8Fo.html
http://www.yqcq.gov.cn/e/space/?userid=158255&yqcq.xml?feed_filter=20160910Ae8Pc.html
http://www.yqcq.gov.cn/e/space/?userid=158257&yqcq.xml?feed_filter=20160910Fh3Fq.html
http://www.yqcq.gov.cn/e/space/?userid=158258&yqcq.xml?feed_filter=20160910Rg9Dt.html
http://www.yqcq.gov.cn/e/space/?userid=158260&yqcq.xml?feed_filter=20160910Ey4Cj.html
http://www.yqcq.gov.cn/e/space/?userid=158262&yqcq.xml?feed_filter=20160910Fs1Kd.html
http://www.yqcq.gov.cn/e/space/?userid=158263&yqcq.xml?feed_filter=20160910Jc6Yk.html
http://www.yqcq.gov.cn/e/space/?userid=158264&yqcq.xml?feed_filter=20160910Xs5Kn.html
http://www.yqcq.gov.cn/e/space/?userid=158265&yqcq.xml?feed_filter=20160910Ar1Hf.html
http://www.yqcq.gov.cn/e/space/?userid=158267&yqcq.xml?feed_filter=20160910Rw1Pv.html
http://www.yqcq.gov.cn/e/space/?userid=158268&yqcq.xml?feed_filter=20160910Dv1Ca.html
http://www.yqcq.gov.cn/e/space/?userid=158269&yqcq.xml?feed_filter=20160910Or9Ic.html
http://www.yqcq.gov.cn/e/space/?userid=158270&yqcq.xml?feed_filter=20160910Jc6Rb.html
http://www.yqcq.gov.cn/e/space/?userid=158272&yqcq.xml?feed_filter=20160910Dp8Oz.html
http://www.yqcq.gov.cn/e/space/?userid=158273&yqcq.xml?feed_filter=20160910Rh3Jh.html
http://www.yqcq.gov.cn/e/space/?userid=158274&yqcq.xml?feed_filter=20160910Kc2Td.html
http://www.yqcq.gov.cn/e/space/?userid=158275&yqcq.xml?feed_filter=20160910Bc4Gp.html
http://www.yqcq.gov.cn/e/space/?userid=158276&yqcq.xml?feed_filter=20160910Jg5Ne.html
http://www.yqcq.gov.cn/e/space/?userid=158277&yqcq.xml?feed_filter=20160910Or1Wx.html
http://www.yqcq.gov.cn/e/space/?userid=158279&yqcq.xml?feed_filter=20160910Td4Xo.html
http://www.yqcq.gov.cn/e/space/?userid=158280&yqcq.xml?feed_filter=20160910Di7Gd.html
http://www.yqcq.gov.cn/e/space/?userid=158281&yqcq.xml?feed_filter=20160910Nt9Ho.html
http://www.yqcq.gov.cn/e/space/?userid=158283&yqcq.xml?feed_filter=20160910Md9Dj.html
http://www.yqcq.gov.cn/e/space/?userid=158284&yqcq.xml?feed_filter=20160910Kk4Az.html
http://www.yqcq.gov.cn/e/space/?userid=158286&yqcq.xml?feed_filter=20160910Aq9Bk.html
http://www.yqcq.gov.cn/e/space/?userid=158287&yqcq.xml?feed_filter=20160910Tu4Rl.html
http://www.yqcq.gov.cn/e/space/?userid=158288&yqcq.xml?feed_filter=20160910Cx5Aq.html
http://www.yqcq.gov.cn/e/space/?userid=158290&yqcq.xml?feed_filter=20160910Yt0Bl.html
http://www.yqcq.gov.cn/e/space/?userid=158291&yqcq.xml?feed_filter=20160910Kl0Lr.html
http://www.yqcq.gov.cn/e/space/?userid=158295&yqcq.xml?feed_filter=20160910Bp8Ly.html
http://www.yqcq.gov.cn/e/space/?userid=158299&yqcq.xml?feed_filter=20160910Su8Cy.html
http://www.yqcq.gov.cn/e/space/?userid=158302&yqcq.xml?feed_filter=20160910Vn6Uu.html
http://www.yqcq.gov.cn/e/space/?userid=158303&yqcq.xml?feed_filter=20160910Le7Mq.html
http://www.yqcq.gov.cn/e/space/?userid=158307&yqcq.xml?feed_filter=20160910Rh5Va.html
http://www.yqcq.gov.cn/e/space/?userid=158308&yqcq.xml?feed_filter=20160910Jb5Ex.html
http://www.yqcq.gov.cn/e/space/?userid=158310&yqcq.xml?feed_filter=20160910Rd9Qd.html
http://www.yqcq.gov.cn/e/space/?userid=158311&yqcq.xml?feed_filter=20160910Mp1Bz.html
http://www.yqcq.gov.cn/e/space/?userid=158314&yqcq.xml?feed_filter=20160910Qt2Yd.html
http://www.yqcq.gov.cn/e/space/?userid=158315&yqcq.xml?feed_filter=20160910Am0Ej.html
http://www.yqcq.gov.cn/e/space/?userid=158317&yqcq.xml?feed_filter=20160910Zp8Hh.html
http://www.yqcq.gov.cn/e/space/?userid=158318&yqcq.xml?feed_filter=20160910Im2Mi.html
http://www.yqcq.gov.cn/e/space/?userid=158320&yqcq.xml?feed_filter=20160910Ms2Yy.html
http://www.yqcq.gov.cn/e/space/?userid=158321&yqcq.xml?feed_filter=20160910Gh1Ej.html
http://www.yqcq.gov.cn/e/space/?userid=158323&yqcq.xml?feed_filter=20160910Qj0Vi.html
http://www.yqcq.gov.cn/e/space/?userid=158324&yqcq.xml?feed_filter=20160910Hp9Al.html
http://www.yqcq.gov.cn/e/space/?userid=158325&yqcq.xml?feed_filter=20160910Oi6In.html
http://www.yqcq.gov.cn/e/space/?userid=158327&yqcq.xml?feed_filter=20160910Or7Nk.html
http://www.yqcq.gov.cn/e/space/?userid=158328&yqcq.xml?feed_filter=20160910Cm4Ju.html
http://www.yqcq.gov.cn/e/space/?userid=158330&yqcq.xml?feed_filter=20160910Gl0Yw.html
http://www.yqcq.gov.cn/e/space/?userid=158331&yqcq.xml?feed_filter=20160910Kt2Fw.html
http://www.yqcq.gov.cn/e/space/?userid=158333&yqcq.xml?feed_filter=20160910Dv1Yc.html
http://www.yqcq.gov.cn/e/space/?userid=158334&yqcq.xml?feed_filter=20160910Rj7Yk.html
http://www.yqcq.gov.cn/e/space/?userid=158336&yqcq.xml?feed_filter=20160910Dr5Et.html
http://www.yqcq.gov.cn/e/space/?userid=158337&yqcq.xml?feed_filter=20160910Ke4Lc.html
http://www.yqcq.gov.cn/e/space/?userid=158338&yqcq.xml?feed_filter=20160910Jf5Js.html
http://www.yqcq.gov.cn/e/space/?userid=158339&yqcq.xml?feed_filter=20160910Mi0Hq.html
http://www.yqcq.gov.cn/e/space/?userid=158341&yqcq.xml?feed_filter=20160910Un6Ah.html
http://www.yqcq.gov.cn/e/space/?userid=158342&yqcq.xml?feed_filter=20160910Cz1Mw.html
http://www.yqcq.gov.cn/e/space/?userid=158344&yqcq.xml?feed_filter=20160910Xl1Zu.html
http://www.yqcq.gov.cn/e/space/?userid=158345&yqcq.xml?feed_filter=20160910Mg7Uj.html
http://www.yqcq.gov.cn/e/space/?userid=158347&yqcq.xml?feed_filter=20160910Oa9Th.html
http://www.yqcq.gov.cn/e/space/?userid=158348&yqcq.xml?feed_filter=20160910Ml3Fo.html
http://www.yqcq.gov.cn/e/space/?userid=158352&yqcq.xml?feed_filter=20160910Kq2Qg.html
http://www.yqcq.gov.cn/e/space/?userid=158357&yqcq.xml?feed_filter=20160910Tr1Fy.html
http://www.yqcq.gov.cn/e/space/?userid=158361&yqcq.xml?feed_filter=20160910Qh6Zx.html
http://www.yqcq.gov.cn/e/space/?userid=158363&yqcq.xml?feed_filter=20160910Mp5Bo.html
http://www.yqcq.gov.cn/e/space/?userid=158364&yqcq.xml?feed_filter=20160910Mr8Em.html
http://www.yqcq.gov.cn/e/space/?userid=158366&yqcq.xml?feed_filter=20160910Pv6Oe.html
http://www.yqcq.gov.cn/e/space/?userid=158369&yqcq.xml?feed_filter=20160910Gk6Yr.html
http://www.yqcq.gov.cn/e/space/?userid=158371&yqcq.xml?feed_filter=20160910Br0Li.html
http://www.yqcq.gov.cn/e/space/?userid=158372&yqcq.xml?feed_filter=20160910Fs2Me.html
http://www.yqcq.gov.cn/e/space/?userid=158374&yqcq.xml?feed_filter=20160910Va2Sq.html
http://www.yqcq.gov.cn/e/space/?userid=158375&yqcq.xml?feed_filter=20160910Qn7Au.html
http://www.yqcq.gov.cn/e/space/?userid=158376&yqcq.xml?feed_filter=20160910Db8Ak.html
http://www.yqcq.gov.cn/e/space/?userid=158378&yqcq.xml?feed_filter=20160910Er7Tu.html
http://www.yqcq.gov.cn/e/space/?userid=158379&yqcq.xml?feed_filter=20160910Aa8Oz.html
http://www.yqcq.gov.cn/e/space/?userid=158380&yqcq.xml?feed_filter=20160910Ti0Rj.html
http://www.yqcq.gov.cn/e/space/?userid=158382&yqcq.xml?feed_filter=20160910Sa1Di.html
http://www.yqcq.gov.cn/e/space/?userid=158383&yqcq.xml?feed_filter=20160910Tr1Vl.html
http://www.yqcq.gov.cn/e/space/?userid=158385&yqcq.xml?feed_filter=20160910Qn1Qm.html
http://www.yqcq.gov.cn/e/space/?userid=158386&yqcq.xml?feed_filter=20160910Mk3Zg.html
http://www.yqcq.gov.cn/e/space/?userid=158387&yqcq.xml?feed_filter=20160910Jx6Jj.html
http://www.yqcq.gov.cn/e/space/?userid=158389&yqcq.xml?feed_filter=20160910Pz0Od.html
http://www.yqcq.gov.cn/e/space/?userid=158390&yqcq.xml?feed_filter=20160910Zy9Pl.html
http://www.yqcq.gov.cn/e/space/?userid=158391&yqcq.xml?feed_filter=20160910Cs6Dh.html
http://www.yqcq.gov.cn/e/space/?userid=158392&yqcq.xml?feed_filter=20160910Lq9Kz.html
http://www.yqcq.gov.cn/e/space/?userid=158394&yqcq.xml?feed_filter=20160910Rr5Gt.html
http://www.yqcq.gov.cn/e/space/?userid=158396&yqcq.xml?feed_filter=20160910Ez2Yu.html
http://www.yqcq.gov.cn/e/space/?userid=158400&yqcq.xml?feed_filter=20160910Su1Dr.html
http://www.yqcq.gov.cn/e/space/?userid=158402&yqcq.xml?feed_filter=20160910Up6Ou.html
http://www.yqcq.gov.cn/e/space/?userid=158403&yqcq.xml?feed_filter=20160910Yb9Xf.html
http://www.yqcq.gov.cn/e/space/?userid=158405&yqcq.xml?feed_filter=20160910Lc7Pw.html
http://www.yqcq.gov.cn/e/space/?userid=158408&yqcq.xml?feed_filter=20160910Lr2Wx.html
http://www.yqcq.gov.cn/e/space/?userid=158411&yqcq.xml?feed_filter=20160910Vb3Eh.html
http://www.yqcq.gov.cn/e/space/?userid=158413&yqcq.xml?feed_filter=20160910No0Ft.html
http://www.yqcq.gov.cn/e/space/?userid=158415&yqcq.xml?feed_filter=20160910Rq3Kx.html
http://www.yqcq.gov.cn/e/space/?userid=158417&yqcq.xml?feed_filter=20160910Aw5Rl.html
http://www.yqcq.gov.cn/e/space/?userid=158419&yqcq.xml?feed_filter=20160910Ba4Ft.html
http://www.yqcq.gov.cn/e/space/?userid=158420&yqcq.xml?feed_filter=20160910Hl6Xb.html
http://www.yqcq.gov.cn/e/space/?userid=158422&yqcq.xml?feed_filter=20160910Bs6Ji.html
http://www.yqcq.gov.cn/e/space/?userid=158423&yqcq.xml?feed_filter=20160910Db5Cd.html
http://www.yqcq.gov.cn/e/space/?userid=158426&yqcq.xml?feed_filter=20160910Mk7Zq.html
http://www.yqcq.gov.cn/e/space/?userid=158427&yqcq.xml?feed_filter=20160910Ym2Hf.html
http://www.yqcq.gov.cn/e/space/?userid=158428&yqcq.xml?feed_filter=20160910Sq7Zy.html
http://www.yqcq.gov.cn/e/space/?userid=158430&yqcq.xml?feed_filter=20160910Hc4Dw.html
http://www.yqcq.gov.cn/e/space/?userid=158431&yqcq.xml?feed_filter=20160910Ir5Mo.html
http://www.yqcq.gov.cn/e/space/?userid=158432&yqcq.xml?feed_filter=20160910Vh7Lz.html
http://www.yqcq.gov.cn/e/space/?userid=158433&yqcq.xml?feed_filter=20160910Rw0Nv.html
http://www.yqcq.gov.cn/e/space/?userid=158435&yqcq.xml?feed_filter=20160910Cs8Jl.html
http://www.yqcq.gov.cn/e/space/?userid=158437&yqcq.xml?feed_filter=20160910Hp6Ba.html
http://www.yqcq.gov.cn/e/space/?userid=158438&yqcq.xml?feed_filter=20160910Ph7Su.html
http://www.yqcq.gov.cn/e/space/?userid=158439&yqcq.xml?feed_filter=20160910Rd1Vv.html
http://www.yqcq.gov.cn/e/space/?userid=158440&yqcq.xml?feed_filter=20160910Cr0Ka.html
http://www.yqcq.gov.cn/e/space/?userid=158441&yqcq.xml?feed_filter=20160910Qa5Zh.html
http://www.yqcq.gov.cn/e/space/?userid=158443&yqcq.xml?feed_filter=20160910El8Da.html
http://www.yqcq.gov.cn/e/space/?userid=158444&yqcq.xml?feed_filter=20160910Re9Yb.html
http://www.yqcq.gov.cn/e/space/?userid=158445&yqcq.xml?feed_filter=20160910Qt7Ft.html
http://www.yqcq.gov.cn/e/space/?userid=158447&yqcq.xml?feed_filter=20160910Ql9Gv.html
http://www.yqcq.gov.cn/e/space/?userid=158449&yqcq.xml?feed_filter=20160910Qv9Ae.html
http://www.yqcq.gov.cn/e/space/?userid=158450&yqcq.xml?feed_filter=20160910Tz1Oh.html
http://www.yqcq.gov.cn/e/space/?userid=158452&yqcq.xml?feed_filter=20160910Dm1Bx.html
http://www.yqcq.gov.cn/e/space/?userid=158453&yqcq.xml?feed_filter=20160910Fh0Eh.html
http://www.yqcq.gov.cn/e/space/?userid=158455&yqcq.xml?feed_filter=20160910Qb7Lw.html
http://www.yqcq.gov.cn/e/space/?userid=158456&yqcq.xml?feed_filter=20160910Xt8Tr.html
http://www.yqcq.gov.cn/e/space/?userid=158458&yqcq.xml?feed_filter=20160910Zc9Df.html
http://www.yqcq.gov.cn/e/space/?userid=158459&yqcq.xml?feed_filter=20160910Kk8Ub.html
http://www.yqcq.gov.cn/e/space/?userid=158460&yqcq.xml?feed_filter=20160910Cy6Ta.html
http://www.yqcq.gov.cn/e/space/?userid=158462&yqcq.xml?feed_filter=20160910Ga1Jt.html
http://www.yqcq.gov.cn/e/space/?userid=158463&yqcq.xml?feed_filter=20160910Yp4On.html
http://www.yqcq.gov.cn/e/space/?userid=158464&yqcq.xml?feed_filter=20160910Jy6Jn.html
http://www.yqcq.gov.cn/e/space/?userid=158466&yqcq.xml?feed_filter=20160910Kj6Rq.html
http://www.yqcq.gov.cn/e/space/?userid=158467&yqcq.xml?feed_filter=20160910Bs1Qd.html
http://www.yqcq.gov.cn/e/space/?userid=158468&yqcq.xml?feed_filter=20160910Lo0Dj.html
http://www.yqcq.gov.cn/e/space/?userid=158470&yqcq.xml?feed_filter=20160910Es0Fd.html
http://www.yqcq.gov.cn/e/space/?userid=158471&yqcq.xml?feed_filter=20160910Yu2Du.html
http://www.yqcq.gov.cn/e/space/?userid=158472&yqcq.xml?feed_filter=20160910Cd1Cd.html
http://www.yqcq.gov.cn/e/space/?userid=158474&yqcq.xml?feed_filter=20160910Fx3Wy.html
http://www.yqcq.gov.cn/e/space/?userid=158475&yqcq.xml?feed_filter=20160910Bm6Il.html
http://www.yqcq.gov.cn/e/space/?userid=158477&yqcq.xml?feed_filter=20160910Wl3Po.html
http://www.yqcq.gov.cn/e/space/?userid=158478&yqcq.xml?feed_filter=20160910Rr3Sk.html
http://www.yqcq.gov.cn/e/space/?userid=158479&yqcq.xml?feed_filter=20160910Yz5Ab.html
http://www.yqcq.gov.cn/e/space/?userid=158481&yqcq.xml?feed_filter=20160910Qv4Tz.html
http://www.yqcq.gov.cn/e/space/?userid=158482&yqcq.xml?feed_filter=20160910An5St.html
http://www.yqcq.gov.cn/e/space/?userid=158484&yqcq.xml?feed_filter=20160910Xk4Ie.html
http://www.yqcq.gov.cn/e/space/?userid=158485&yqcq.xml?feed_filter=20160910Ug3We.html
http://www.yqcq.gov.cn/e/space/?userid=158486&yqcq.xml?feed_filter=20160910Vm0Ba.html
http://www.yqcq.gov.cn/e/space/?userid=158487&yqcq.xml?feed_filter=20160910Px4Fj.html
http://www.yqcq.gov.cn/e/space/?userid=158489&yqcq.xml?feed_filter=20160910Tt0Xe.html
http://www.yqcq.gov.cn/e/space/?userid=158490&yqcq.xml?feed_filter=20160910Cm0Iv.html
http://www.yqcq.gov.cn/e/space/?userid=158492&yqcq.xml?feed_filter=20160910Rh0Ga.html
http://www.yqcq.gov.cn/e/space/?userid=158493&yqcq.xml?feed_filter=20160910Rj9Sz.html
http://www.yqcq.gov.cn/e/space/?userid=158494&yqcq.xml?feed_filter=20160910Hs5Xp.html
http://www.yqcq.gov.cn/e/space/?userid=158496&yqcq.xml?feed_filter=20160910Jv0Sx.html
http://www.yqcq.gov.cn/e/space/?userid=158497&yqcq.xml?feed_filter=20160910Aa3Ip.html
http://www.yqcq.gov.cn/e/space/?userid=158499&yqcq.xml?feed_filter=20160910Nv3Ad.html
http://www.yqcq.gov.cn/e/space/?userid=158500&yqcq.xml?feed_filter=20160910Nt0Sv.html
http://www.yqcq.gov.cn/e/space/?userid=158502&yqcq.xml?feed_filter=20160910Fh0Hn.html
http://www.yqcq.gov.cn/e/space/?userid=158504&yqcq.xml?feed_filter=20160910Wg7Qg.html
http://www.yqcq.gov.cn/e/space/?userid=158505&yqcq.xml?feed_filter=20160910Ec8Zt.html
http://www.yqcq.gov.cn/e/space/?userid=158507&yqcq.xml?feed_filter=20160910Wx0Ts.html
http://www.yqcq.gov.cn/e/space/?userid=158508&yqcq.xml?feed_filter=20160910Vc3An.html
http://www.yqcq.gov.cn/e/space/?userid=158510&yqcq.xml?feed_filter=20160910Eh9Cg.html
http://www.yqcq.gov.cn/e/space/?userid=158511&yqcq.xml?feed_filter=20160910Gl8Vf.html
http://www.yqcq.gov.cn/e/space/?userid=158513&yqcq.xml?feed_filter=20160910Hp9Bj.html
http://www.yqcq.gov.cn/e/space/?userid=158514&yqcq.xml?feed_filter=20160910Nx3Lj.html
http://www.yqcq.gov.cn/e/space/?userid=158515&yqcq.xml?feed_filter=20160910Pw2Lb.html
http://www.yqcq.gov.cn/e/space/?userid=158517&yqcq.xml?feed_filter=20160910Ly2Tf.html
http://www.yqcq.gov.cn/e/space/?userid=158519&yqcq.xml?feed_filter=20160910Od7Tp.html
http://www.yqcq.gov.cn/e/space/?userid=158520&yqcq.xml?feed_filter=20160910Dg2Gi.html
http://www.yqcq.gov.cn/e/space/?userid=158522&yqcq.xml?feed_filter=20160910Ho4Oh.html
http://www.yqcq.gov.cn/e/space/?userid=158523&yqcq.xml?feed_filter=20160910Sf5Yf.html
http://www.yqcq.gov.cn/e/space/?userid=158524&yqcq.xml?feed_filter=20160910Zk9Vm.html
http://www.yqcq.gov.cn/e/space/?userid=158526&yqcq.xml?feed_filter=20160910Qe0Zv.html
http://www.yqcq.gov.cn/e/space/?userid=158527&yqcq.xml?feed_filter=20160910Bq9Nd.html
http://www.yqcq.gov.cn/e/space/?userid=158529&yqcq.xml?feed_filter=20160910Tj5Hi.html
http://www.yqcq.gov.cn/e/space/?userid=158530&yqcq.xml?feed_filter=20160910Zy0To.html
http://www.yqcq.gov.cn/e/space/?userid=158531&yqcq.xml?feed_filter=20160910Xl8Rk.html
http://www.yqcq.gov.cn/e/space/?userid=158533&yqcq.xml?feed_filter=20160910If4Om.html
http://www.yqcq.gov.cn/e/space/?userid=158534&yqcq.xml?feed_filter=20160910Wr6Ng.html
http://www.yqcq.gov.cn/e/space/?userid=158535&yqcq.xml?feed_filter=20160910Wz0Vn.html
http://www.yqcq.gov.cn/e/space/?userid=158537&yqcq.xml?feed_filter=20160910Wn3Nn.html
http://www.yqcq.gov.cn/e/space/?userid=158538&yqcq.xml?feed_filter=20160910Wu3Um.html
http://www.yqcq.gov.cn/e/space/?userid=158540&yqcq.xml?feed_filter=20160910Lx1Jm.html
http://www.yqcq.gov.cn/e/space/?userid=158542&yqcq.xml?feed_filter=20160910Tu4Yq.html
http://www.yqcq.gov.cn/e/space/?userid=158543&yqcq.xml?feed_filter=20160910Bg5Wt.html
http://www.yqcq.gov.cn/e/space/?userid=158544&yqcq.xml?feed_filter=20160910Vm5Sm.html
http://www.yqcq.gov.cn/e/space/?userid=158546&yqcq.xml?feed_filter=20160910Iz1Eq.html
http://www.yqcq.gov.cn/e/space/?userid=158547&yqcq.xml?feed_filter=20160910Po6Jo.html
http://www.yqcq.gov.cn/e/space/?userid=158548&yqcq.xml?feed_filter=20160910Mg5On.html
http://www.yqcq.gov.cn/e/space/?userid=158550&yqcq.xml?feed_filter=20160910Hd3Cm.html
http://www.yqcq.gov.cn/e/space/?userid=158551&yqcq.xml?feed_filter=20160910Js8Yy.html
http://www.yqcq.gov.cn/e/space/?userid=158553&yqcq.xml?feed_filter=20160910Mg6Yo.html
http://www.yqcq.gov.cn/e/space/?userid=158555&yqcq.xml?feed_filter=20160910Xt9Zb.html
http://www.yqcq.gov.cn/e/space/?userid=158556&yqcq.xml?feed_filter=20160910Ln2Mg.html
http://www.yqcq.gov.cn/e/space/?userid=158558&yqcq.xml?feed_filter=20160910Br4Kc.html
http://www.yqcq.gov.cn/e/space/?userid=158560&yqcq.xml?feed_filter=20160910Kp1Qy.html
http://www.yqcq.gov.cn/e/space/?userid=158561&yqcq.xml?feed_filter=20160910Kc9Qd.html
http://www.yqcq.gov.cn/e/space/?userid=158564&yqcq.xml?feed_filter=20160910Iv1Rv.html
http://www.yqcq.gov.cn/e/space/?userid=158565&yqcq.xml?feed_filter=20160910Mq0Ww.html
http://www.yqcq.gov.cn/e/space/?userid=158566&yqcq.xml?feed_filter=20160910Uk4Yq.html
http://www.yqcq.gov.cn/e/space/?userid=158568&yqcq.xml?feed_filter=20160910Kv7Xa.html
http://www.yqcq.gov.cn/e/space/?userid=158570&yqcq.xml?feed_filter=20160910Cv3Eo.html
http://www.yqcq.gov.cn/e/space/?userid=158571&yqcq.xml?feed_filter=20160910Hn0Kq.html
http://www.yqcq.gov.cn/e/space/?userid=158573&yqcq.xml?feed_filter=20160910Pi5Mr.html
http://www.yqcq.gov.cn/e/space/?userid=158574&yqcq.xml?feed_filter=20160910Xh5Zd.html
http://www.yqcq.gov.cn/e/space/?userid=158577&yqcq.xml?feed_filter=20160910Wk5Bo.html
http://www.yqcq.gov.cn/e/space/?userid=158579&yqcq.xml?feed_filter=20160910Vv5Rf.html
http://www.yqcq.gov.cn/e/space/?userid=158580&yqcq.xml?feed_filter=20160910Pd8Cx.html
http://www.yqcq.gov.cn/e/space/?userid=158582&yqcq.xml?feed_filter=20160910Bq1Xa.html
http://www.yqcq.gov.cn/e/space/?userid=158583&yqcq.xml?feed_filter=20160910Kh1Ok.html
http://www.yqcq.gov.cn/e/space/?userid=158585&yqcq.xml?feed_filter=20160910Il8Cp.html
http://www.yqcq.gov.cn/e/space/?userid=158587&yqcq.xml?feed_filter=20160910Ko1Cl.html
http://www.yqcq.gov.cn/e/space/?userid=158589&yqcq.xml?feed_filter=20160910Pg8Vd.html
http://www.yqcq.gov.cn/e/space/?userid=158590&yqcq.xml?feed_filter=20160910Ea1Uz.html
http://www.yqcq.gov.cn/e/space/?userid=158592&yqcq.xml?feed_filter=20160910Ov7Pq.html
http://www.yqcq.gov.cn/e/space/?userid=158593&yqcq.xml?feed_filter=20160910Vp0Ju.html
http://www.yqcq.gov.cn/e/space/?userid=158595&yqcq.xml?feed_filter=20160910Yb8Lj.html
http://www.yqcq.gov.cn/e/space/?userid=158596&yqcq.xml?feed_filter=20160910Sz6Qe.html
http://www.yqcq.gov.cn/e/space/?userid=158598&yqcq.xml?feed_filter=20160910Cf8Qj.html
http://www.yqcq.gov.cn/e/space/?userid=158600&yqcq.xml?feed_filter=20160910Vk3Uq.html
http://www.yqcq.gov.cn/e/space/?userid=158601&yqcq.xml?feed_filter=20160910Ch2Zf.html
http://www.yqcq.gov.cn/e/space/?userid=158602&yqcq.xml?feed_filter=20160910Yv2Uv.html
http://www.yqcq.gov.cn/e/space/?userid=158604&yqcq.xml?feed_filter=20160910Ic4Wp.html
http://www.yqcq.gov.cn/e/space/?userid=158606&yqcq.xml?feed_filter=20160910Mi1Xf.html
http://www.yqcq.gov.cn/e/space/?userid=158607&yqcq.xml?feed_filter=20160910Xw6Uv.html
http://www.yqcq.gov.cn/e/space/?userid=158608&yqcq.xml?feed_filter=20160910Mf8Ef.html
http://www.yqcq.gov.cn/e/space/?userid=158610&yqcq.xml?feed_filter=20160910Wb2Aq.html
http://www.yqcq.gov.cn/e/space/?userid=158611&yqcq.xml?feed_filter=20160910Km0Jy.html
http://www.yqcq.gov.cn/e/space/?userid=158613&yqcq.xml?feed_filter=20160910Ad2Br.html
http://www.yqcq.gov.cn/e/space/?userid=158614&yqcq.xml?feed_filter=20160910Jj9Xc.html
http://www.yqcq.gov.cn/e/space/?userid=158616&yqcq.xml?feed_filter=20160910Ue8Aj.html
http://www.yqcq.gov.cn/e/space/?userid=158617&yqcq.xml?feed_filter=20160910Um0Yp.html
http://www.yqcq.gov.cn/e/space/?userid=158618&yqcq.xml?feed_filter=20160910Yy2Na.html
http://www.yqcq.gov.cn/e/space/?userid=158620&yqcq.xml?feed_filter=20160910Lr7Mm.html
http://www.yqcq.gov.cn/e/space/?userid=158621&yqcq.xml?feed_filter=20160910Yt2Rl.html
http://www.yqcq.gov.cn/e/space/?userid=158623&yqcq.xml?feed_filter=20160910Nf6Ai.html
http://www.yqcq.gov.cn/e/space/?userid=158624&yqcq.xml?feed_filter=20160910Zi8Yh.html
http://www.yqcq.gov.cn/e/space/?userid=158626&yqcq.xml?feed_filter=20160910Lb2Rw.html
http://www.yqcq.gov.cn/e/space/?userid=158627&yqcq.xml?feed_filter=20160910Mx8Xs.html
http://www.yqcq.gov.cn/e/space/?userid=158629&yqcq.xml?feed_filter=20160910Jx1Tz.html
http://www.yqcq.gov.cn/e/space/?userid=158631&yqcq.xml?feed_filter=20160910Hl6Ua.html
http://www.yqcq.gov.cn/e/space/?userid=158632&yqcq.xml?feed_filter=20160910Dq6Ad.html
http://www.yqcq.gov.cn/e/space/?userid=158633&yqcq.xml?feed_filter=20160910Pf6Eu.html
http://www.yqcq.gov.cn/e/space/?userid=158635&yqcq.xml?feed_filter=20160910Ic9Jo.html
http://www.yqcq.gov.cn/e/space/?userid=158636&yqcq.xml?feed_filter=20160910Xr3Er.html
http://www.yqcq.gov.cn/e/space/?userid=158637&yqcq.xml?feed_filter=20160910Jf0Il.html
http://www.yqcq.gov.cn/e/space/?userid=158639&yqcq.xml?feed_filter=20160910Jt8Lf.html
http://www.yqcq.gov.cn/e/space/?userid=158640&yqcq.xml?feed_filter=20160910Vt0Ur.html
http://www.yqcq.gov.cn/e/space/?userid=158642&yqcq.xml?feed_filter=20160910Yg9Mv.html
http://www.yqcq.gov.cn/e/space/?userid=158643&yqcq.xml?feed_filter=20160910Op3Ck.html
http://www.yqcq.gov.cn/e/space/?userid=158644&yqcq.xml?feed_filter=20160910Tn8Da.html
http://www.yqcq.gov.cn/e/space/?userid=158646&yqcq.xml?feed_filter=20160910Nb1Pz.html
http://www.yqcq.gov.cn/e/space/?userid=158647&yqcq.xml?feed_filter=20160910Kk2Pp.html
http://www.yqcq.gov.cn/e/space/?userid=158649&yqcq.xml?feed_filter=20160910Vg8Kn.html
http://www.yqcq.gov.cn/e/space/?userid=158650&yqcq.xml?feed_filter=20160910Uy5Ma.html
http://www.yqcq.gov.cn/e/space/?userid=158651&yqcq.xml?feed_filter=20160910Mp3Qs.html
http://www.yqcq.gov.cn/e/space/?userid=158653&yqcq.xml?feed_filter=20160910Ml5Wd.html
http://www.yqcq.gov.cn/e/space/?userid=158654&yqcq.xml?feed_filter=20160910Zi5Et.html
http://www.yqcq.gov.cn/e/space/?userid=158656&yqcq.xml?feed_filter=20160910Sp4In.html
http://www.yqcq.gov.cn/e/space/?userid=158657&yqcq.xml?feed_filter=20160910In2Gp.html
http://www.yqcq.gov.cn/e/space/?userid=158659&yqcq.xml?feed_filter=20160910Ci3Lz.html
http://www.yqcq.gov.cn/e/space/?userid=158660&yqcq.xml?feed_filter=20160910Ca2De.html
http://www.yqcq.gov.cn/e/space/?userid=158661&yqcq.xml?feed_filter=20160910Pg3Gc.html
http://www.yqcq.gov.cn/e/space/?userid=158662&yqcq.xml?feed_filter=20160910Wv7Nn.html
http://www.yqcq.gov.cn/e/space/?userid=158664&yqcq.xml?feed_filter=20160910Mp8Ki.html
http://www.yqcq.gov.cn/e/space/?userid=158665&yqcq.xml?feed_filter=20160910Qk4Dd.html
http://www.yqcq.gov.cn/e/space/?userid=158667&yqcq.xml?feed_filter=20160910Sf0Ta.html
http://www.yqcq.gov.cn/e/space/?userid=158669&yqcq.xml?feed_filter=20160910Az4Vu.html
http://www.yqcq.gov.cn/e/space/?userid=158670&yqcq.xml?feed_filter=20160910Xh9Xg.html
http://www.yqcq.gov.cn/e/space/?userid=158671&yqcq.xml?feed_filter=20160910Jj7Js.html
http://www.yqcq.gov.cn/e/space/?userid=158672&yqcq.xml?feed_filter=20160910Tx2Ad.html
http://www.yqcq.gov.cn/e/space/?userid=158674&yqcq.xml?feed_filter=20160910Ra7Ha.html
http://www.yqcq.gov.cn/e/space/?userid=158675&yqcq.xml?feed_filter=20160910Yw7Jk.html
http://www.yqcq.gov.cn/e/space/?userid=158676&yqcq.xml?feed_filter=20160910Ei8Yp.html
http://www.yqcq.gov.cn/e/space/?userid=158677&yqcq.xml?feed_filter=20160910Sp4Md.html
http://www.yqcq.gov.cn/e/space/?userid=158679&yqcq.xml?feed_filter=20160910Qj7Yg.html
http://www.yqcq.gov.cn/e/space/?userid=158680&yqcq.xml?feed_filter=20160910Dc0Pv.html
http://www.yqcq.gov.cn/e/space/?userid=158682&yqcq.xml?feed_filter=20160910Ad2Ao.html
http://www.yqcq.gov.cn/e/space/?userid=158683&yqcq.xml?feed_filter=20160910Hb2Om.html
http://www.yqcq.gov.cn/e/space/?userid=158684&yqcq.xml?feed_filter=20160910Ki7Xr.html
http://www.yqcq.gov.cn/e/space/?userid=158686&yqcq.xml?feed_filter=20160910Kd6It.html
http://www.yqcq.gov.cn/e/space/?userid=158687&yqcq.xml?feed_filter=20160910Vw3Bn.html
http://www.yqcq.gov.cn/e/space/?userid=158688&yqcq.xml?feed_filter=20160910If6Fp.html
http://www.yqcq.gov.cn/e/space/?userid=158689&yqcq.xml?feed_filter=20160910Ib3Mz.html
http://www.yqcq.gov.cn/e/space/?userid=158690&yqcq.xml?feed_filter=20160910Th7Ay.html
http://www.yqcq.gov.cn/e/space/?userid=158691&yqcq.xml?feed_filter=20160910Qm9Xi.html
http://www.yqcq.gov.cn/e/space/?userid=158693&yqcq.xml?feed_filter=20160910Ro3Dx.html
http://www.yqcq.gov.cn/e/space/?userid=158694&yqcq.xml?feed_filter=20160910Lp5Dk.html
http://www.yqcq.gov.cn/e/space/?userid=158695&yqcq.xml?feed_filter=20160910Ge2Tj.html
http://www.yqcq.gov.cn/e/space/?userid=158697&yqcq.xml?feed_filter=20160910Xq3Ug.html
http://www.yqcq.gov.cn/e/space/?userid=158698&yqcq.xml?feed_filter=20160910Nh8Tk.html
http://www.yqcq.gov.cn/e/space/?userid=158700&yqcq.xml?feed_filter=20160910Uj9Oi.html
http://www.yqcq.gov.cn/e/space/?userid=158701&yqcq.xml?feed_filter=20160910Hb8Sb.html
http://www.yqcq.gov.cn/e/space/?userid=158702&yqcq.xml?feed_filter=20160910Cg3It.html
http://www.yqcq.gov.cn/e/space/?userid=158704&yqcq.xml?feed_filter=20160910Yw9Zr.html
http://www.yqcq.gov.cn/e/space/?userid=158705&yqcq.xml?feed_filter=20160910Jr5Yq.html
http://www.yqcq.gov.cn/e/space/?userid=158706&yqcq.xml?feed_filter=20160910Im9Xy.html
http://www.yqcq.gov.cn/e/space/?userid=158708&yqcq.xml?feed_filter=20160910Bs5Fl.html
http://www.yqcq.gov.cn/e/space/?userid=158709&yqcq.xml?feed_filter=20160910Fx4Pr.html
http://www.yqcq.gov.cn/e/space/?userid=158710&yqcq.xml?feed_filter=20160910Os1Wj.html
http://www.yqcq.gov.cn/e/space/?userid=158712&yqcq.xml?feed_filter=20160910Kw0Xu.html
http://www.yqcq.gov.cn/e/space/?userid=158713&yqcq.xml?feed_filter=20160910Ch5Un.html
http://www.yqcq.gov.cn/e/space/?userid=158714&yqcq.xml?feed_filter=20160910Bf8Yo.html
http://www.yqcq.gov.cn/e/space/?userid=158715&yqcq.xml?feed_filter=20160910Cs6Mc.html
http://www.yqcq.gov.cn/e/space/?userid=158717&yqcq.xml?feed_filter=20160910Qi4Jw.html
http://www.yqcq.gov.cn/e/space/?userid=158718&yqcq.xml?feed_filter=20160910Dh5Aw.html
http://www.yqcq.gov.cn/e/space/?userid=158720&yqcq.xml?feed_filter=20160910Ar8Bi.html
http://www.yqcq.gov.cn/e/space/?userid=158721&yqcq.xml?feed_filter=20160910Ix4Nl.html
http://www.yqcq.gov.cn/e/space/?userid=158722&yqcq.xml?feed_filter=20160910Ao7Dx.html
http://www.yqcq.gov.cn/e/space/?userid=158723&yqcq.xml?feed_filter=20160910Ns5Ni.html
http://www.yqcq.gov.cn/e/space/?userid=158725&yqcq.xml?feed_filter=20160910Wb2Gd.html
http://www.yqcq.gov.cn/e/space/?userid=158726&yqcq.xml?feed_filter=20160910Yp9Sk.html
http://www.yqcq.gov.cn/e/space/?userid=158727&yqcq.xml?feed_filter=20160910Tc1Pd.html
http://www.yqcq.gov.cn/e/space/?userid=158729&yqcq.xml?feed_filter=20160910Uy8Hd.html
http://www.yqcq.gov.cn/e/space/?userid=158730&yqcq.xml?feed_filter=20160910Wr6Pk.html
http://www.yqcq.gov.cn/e/space/?userid=158731&yqcq.xml?feed_filter=20160910Qw6Tg.html
http://www.yqcq.gov.cn/e/space/?userid=158733&yqcq.xml?feed_filter=20160910Ly4Xa.html
http://www.yqcq.gov.cn/e/space/?userid=158734&yqcq.xml?feed_filter=20160910Rl2Je.html
http://www.yqcq.gov.cn/e/space/?userid=158736&yqcq.xml?feed_filter=20160910Sy9Lo.html
http://www.yqcq.gov.cn/e/space/?userid=158738&yqcq.xml?feed_filter=20160910Dc4Cp.html
http://www.yqcq.gov.cn/e/space/?userid=158739&yqcq.xml?feed_filter=20160910Gr9Ed.html
http://www.yqcq.gov.cn/e/space/?userid=158740&yqcq.xml?feed_filter=20160910Qb2Aa.html
http://www.yqcq.gov.cn/e/space/?userid=158742&yqcq.xml?feed_filter=20160910Ad6Nh.html
http://www.yqcq.gov.cn/e/space/?userid=158743&yqcq.xml?feed_filter=20160910Uk9Tu.html
http://www.yqcq.gov.cn/e/space/?userid=158745&yqcq.xml?feed_filter=20160910Xy9Ff.html
http://www.yqcq.gov.cn/e/space/?userid=158746&yqcq.xml?feed_filter=20160910Dh3Gd.html
http://www.yqcq.gov.cn/e/space/?userid=158748&yqcq.xml?feed_filter=20160910Wa5Tm.html
http://www.yqcq.gov.cn/e/space/?userid=158749&yqcq.xml?feed_filter=20160910Zk3Fk.html
http://www.yqcq.gov.cn/e/space/?userid=158751&yqcq.xml?feed_filter=20160910Np0Bw.html
http://www.yqcq.gov.cn/e/space/?userid=158752&yqcq.xml?feed_filter=20160910Hg1Re.html
http://www.yqcq.gov.cn/e/space/?userid=158753&yqcq.xml?feed_filter=20160910Uo2Qk.html
http://www.yqcq.gov.cn/e/space/?userid=158755&yqcq.xml?feed_filter=20160910Kq3Dd.html
http://www.yqcq.gov.cn/e/space/?userid=158757&yqcq.xml?feed_filter=20160910Kr9Em.html
http://www.yqcq.gov.cn/e/space/?userid=158759&yqcq.xml?feed_filter=20160910Fc0An.html
http://www.yqcq.gov.cn/e/space/?userid=158760&yqcq.xml?feed_filter=20160910Gl4Sx.html
http://www.yqcq.gov.cn/e/space/?userid=158761&yqcq.xml?feed_filter=20160910Cb6Hv.html
http://www.yqcq.gov.cn/e/space/?userid=158763&yqcq.xml?feed_filter=20160910Sj4As.html
http://www.yqcq.gov.cn/e/space/?userid=158764&yqcq.xml?feed_filter=20160910Kh9Wo.html
http://www.yqcq.gov.cn/e/space/?userid=158765&yqcq.xml?feed_filter=20160910Db9Vz.html
http://www.yqcq.gov.cn/e/space/?userid=158767&yqcq.xml?feed_filter=20160910Km2Sx.html
http://www.yqcq.gov.cn/e/space/?userid=158768&yqcq.xml?feed_filter=20160910Mz5Sx.html
http://www.yqcq.gov.cn/e/space/?userid=158770&yqcq.xml?feed_filter=20160910Ea2Xs.html
http://www.yqcq.gov.cn/e/space/?userid=158771&yqcq.xml?feed_filter=20160910Vt4We.html
http://www.yqcq.gov.cn/e/space/?userid=158773&yqcq.xml?feed_filter=20160910Kf8Ef.html
http://www.yqcq.gov.cn/e/space/?userid=158775&yqcq.xml?feed_filter=20160910Nt4Qr.html
http://www.yqcq.gov.cn/e/space/?userid=158776&yqcq.xml?feed_filter=20160910Dr5Bi.html
http://www.yqcq.gov.cn/e/space/?userid=158778&yqcq.xml?feed_filter=20160910Ho6Ad.html
http://www.yqcq.gov.cn/e/space/?userid=158781&yqcq.xml?feed_filter=20160910Kt0Bw.html
http://www.yqcq.gov.cn/e/space/?userid=158782&yqcq.xml?feed_filter=20160910Dr5Jc.html
http://www.yqcq.gov.cn/e/space/?userid=158784&yqcq.xml?feed_filter=20160910Pf4Td.html
http://www.yqcq.gov.cn/e/space/?userid=158785&yqcq.xml?feed_filter=20160910Ou1Lj.html
http://www.yqcq.gov.cn/e/space/?userid=158786&yqcq.xml?feed_filter=20160910Na0Vz.html
http://www.yqcq.gov.cn/e/space/?userid=158787&yqcq.xml?feed_filter=20160910Fi4Ed.html
http://www.yqcq.gov.cn/e/space/?userid=158789&yqcq.xml?feed_filter=20160910Vz3Gs.html
http://www.yqcq.gov.cn/e/space/?userid=158790&yqcq.xml?feed_filter=20160910Wd5Re.html
http://www.yqcq.gov.cn/e/space/?userid=158791&yqcq.xml?feed_filter=20160910Ro5Kh.html
http://www.yqcq.gov.cn/e/space/?userid=158793&yqcq.xml?feed_filter=20160910Zr8Zv.html
http://www.yqcq.gov.cn/e/space/?userid=158794&yqcq.xml?feed_filter=20160910Mx0Ea.html
http://www.yqcq.gov.cn/e/space/?userid=158795&yqcq.xml?feed_filter=20160910Za9Ad.html
http://www.yqcq.gov.cn/e/space/?userid=158797&yqcq.xml?feed_filter=20160910Ji4Ab.html
http://www.yqcq.gov.cn/e/space/?userid=158799&yqcq.xml?feed_filter=20160910Ro5Uc.html
http://www.yqcq.gov.cn/e/space/?userid=158800&yqcq.xml?feed_filter=20160910Uz8Nw.html
http://www.yqcq.gov.cn/e/space/?userid=158802&yqcq.xml?feed_filter=20160910Ek6Ue.html
http://www.yqcq.gov.cn/e/space/?userid=158803&yqcq.xml?feed_filter=20160910Wn1Qq.html
http://www.yqcq.gov.cn/e/space/?userid=158805&yqcq.xml?feed_filter=20160910Gc4Ms.html
http://www.yqcq.gov.cn/e/space/?userid=158806&yqcq.xml?feed_filter=20160910Cw7Iu.html
http://www.yqcq.gov.cn/e/space/?userid=158807&yqcq.xml?feed_filter=20160910Tz4Jn.html
http://www.yqcq.gov.cn/e/space/?userid=158810&yqcq.xml?feed_filter=20160910Yr2Ax.html
http://www.yqcq.gov.cn/e/space/?userid=158811&yqcq.xml?feed_filter=20160910Xa9Jy.html
http://www.yqcq.gov.cn/e/space/?userid=158813&yqcq.xml?feed_filter=20160910Pw8Dt.html
http://www.yqcq.gov.cn/e/space/?userid=158814&yqcq.xml?feed_filter=20160910Kt9Ee.html
http://www.yqcq.gov.cn/e/space/?userid=158815&yqcq.xml?feed_filter=20160910Na8Ow.html
http://www.yqcq.gov.cn/e/space/?userid=158816&yqcq.xml?feed_filter=20160910Oc4Jn.html
http://www.yqcq.gov.cn/e/space/?userid=158817&yqcq.xml?feed_filter=20160910Qi2Lv.html
http://www.yqcq.gov.cn/e/space/?userid=158819&yqcq.xml?feed_filter=20160910Fv2Df.html
http://www.yqcq.gov.cn/e/space/?userid=158820&yqcq.xml?feed_filter=20160910Uo0Bd.html
http://www.yqcq.gov.cn/e/space/?userid=158821&yqcq.xml?feed_filter=20160910Dm3Ej.html
http://www.yqcq.gov.cn/e/space/?userid=158823&yqcq.xml?feed_filter=20160910En9Bi.html
http://www.yqcq.gov.cn/e/space/?userid=158824&yqcq.xml?feed_filter=20160910Qm6Ac.html
http://www.yqcq.gov.cn/e/space/?userid=158826&yqcq.xml?feed_filter=20160910Ir7Ub.html
http://www.yqcq.gov.cn/e/space/?userid=158827&yqcq.xml?feed_filter=20160910Fe0Gw.html
http://www.yqcq.gov.cn/e/space/?userid=158829&yqcq.xml?feed_filter=20160910Ms9Bl.html
http://www.yqcq.gov.cn/e/space/?userid=158830&yqcq.xml?feed_filter=20160910Vk9My.html
http://www.yqcq.gov.cn/e/space/?userid=158831&yqcq.xml?feed_filter=20160910Xt6Hm.html
http://www.yqcq.gov.cn/e/space/?userid=158833&yqcq.xml?feed_filter=20160910Jl1Jj.html
http://www.yqcq.gov.cn/e/space/?userid=158834&yqcq.xml?feed_filter=20160910Ma5Jt.html
http://www.yqcq.gov.cn/e/space/?userid=158835&yqcq.xml?feed_filter=20160910Jh9Yb.html
http://www.yqcq.gov.cn/e/space/?userid=158837&yqcq.xml?feed_filter=20160910Dp6Fn.html
http://www.yqcq.gov.cn/e/space/?userid=158838&yqcq.xml?feed_filter=20160910Eg1Qn.html
http://www.yqcq.gov.cn/e/space/?userid=158839&yqcq.xml?feed_filter=20160910Nq3Ca.html
http://www.yqcq.gov.cn/e/space/?userid=158841&yqcq.xml?feed_filter=20160910Qo1Ia.html
http://www.yqcq.gov.cn/e/space/?userid=158842&yqcq.xml?feed_filter=20160910Nv4Jr.html
http://www.yqcq.gov.cn/e/space/?userid=158843&yqcq.xml?feed_filter=20160910Dl2Dq.html
http://www.yqcq.gov.cn/e/space/?userid=158844&yqcq.xml?feed_filter=20160910Dz2Bg.html
http://www.yqcq.gov.cn/e/space/?userid=158846&yqcq.xml?feed_filter=20160910Pm4Kb.html
http://www.yqcq.gov.cn/e/space/?userid=158847&yqcq.xml?feed_filter=20160910Ip8Jq.html
http://www.yqcq.gov.cn/e/space/?userid=158848&yqcq.xml?feed_filter=20160910Zt0Tu.html
http://www.yqcq.gov.cn/e/space/?userid=158850&yqcq.xml?feed_filter=20160910Jf3Sy.html
http://www.yqcq.gov.cn/e/space/?userid=158852&yqcq.xml?feed_filter=20160910Pl4Nu.html
http://www.yqcq.gov.cn/e/space/?userid=158853&yqcq.xml?feed_filter=20160910Yg1Jq.html
http://www.yqcq.gov.cn/e/space/?userid=158855&yqcq.xml?feed_filter=20160910Lr8Dg.html
http://www.yqcq.gov.cn/e/space/?userid=158857&yqcq.xml?feed_filter=20160910Bm5Pz.html
http://www.yqcq.gov.cn/e/space/?userid=158858&yqcq.xml?feed_filter=20160910Gl7Sv.html
http://www.yqcq.gov.cn/e/space/?userid=158860&yqcq.xml?feed_filter=20160910Bp3Bc.html
http://www.yqcq.gov.cn/e/space/?userid=158861&yqcq.xml?feed_filter=20160910Hf3Db.html
http://www.yqcq.gov.cn/e/space/?userid=158863&yqcq.xml?feed_filter=20160910Hh3Vn.html
http://www.yqcq.gov.cn/e/space/?userid=158864&yqcq.xml?feed_filter=20160910Gx4Hi.html
http://www.yqcq.gov.cn/e/space/?userid=158865&yqcq.xml?feed_filter=20160910Uo0Ym.html
http://www.yqcq.gov.cn/e/space/?userid=158866&yqcq.xml?feed_filter=20160910Gx9Dn.html
http://www.yqcq.gov.cn/e/space/?userid=158867&yqcq.xml?feed_filter=20160910Xs2Px.html
http://www.yqcq.gov.cn/e/space/?userid=158869&yqcq.xml?feed_filter=20160910Gu6Iz.html
http://www.yqcq.gov.cn/e/space/?userid=158871&yqcq.xml?feed_filter=20160910Ss5Ho.html
http://www.yqcq.gov.cn/e/space/?userid=158872&yqcq.xml?feed_filter=20160910Al9Ai.html
http://www.yqcq.gov.cn/e/space/?userid=158874&yqcq.xml?feed_filter=20160910Pa9Hv.html
http://www.yqcq.gov.cn/e/space/?userid=158875&yqcq.xml?feed_filter=20160910Gu5Ez.html
http://www.yqcq.gov.cn/e/space/?userid=158877&yqcq.xml?feed_filter=20160910Zp9Go.html
http://www.yqcq.gov.cn/e/space/?userid=158878&yqcq.xml?feed_filter=20160910Ba8Sd.html
http://www.yqcq.gov.cn/e/space/?userid=158879&yqcq.xml?feed_filter=20160910Xg8Nr.html
http://www.yqcq.gov.cn/e/space/?userid=158880&yqcq.xml?feed_filter=20160910Wp3Oy.html
http://www.yqcq.gov.cn/e/space/?userid=158882&yqcq.xml?feed_filter=20160910Vt0Ec.html
http://www.yqcq.gov.cn/e/space/?userid=158883&yqcq.xml?feed_filter=20160910Uz0Fr.html
http://www.yqcq.gov.cn/e/space/?userid=158884&yqcq.xml?feed_filter=20160910Wy7Ax.html
http://www.yqcq.gov.cn/e/space/?userid=158886&yqcq.xml?feed_filter=20160910Wy3Kt.html
http://www.yqcq.gov.cn/e/space/?userid=158887&yqcq.xml?feed_filter=20160910Lv4Oe.html
http://www.yqcq.gov.cn/e/space/?userid=158888&yqcq.xml?feed_filter=20160910Yw1Ve.html
http://www.yqcq.gov.cn/e/space/?userid=158890&yqcq.xml?feed_filter=20160910Ae7Rb.html
http://www.yqcq.gov.cn/e/space/?userid=158891&yqcq.xml?feed_filter=20160910Cu8Fa.html
http://www.yqcq.gov.cn/e/space/?userid=158892&yqcq.xml?feed_filter=20160910Kq2Ht.html
http://www.yqcq.gov.cn/e/space/?userid=158894&yqcq.xml?feed_filter=20160910Fa3As.html
http://www.yqcq.gov.cn/e/space/?userid=158895&yqcq.xml?feed_filter=20160910Jf0Wr.html
http://www.yqcq.gov.cn/e/space/?userid=158896&yqcq.xml?feed_filter=20160910An6Vr.html
http://www.yqcq.gov.cn/e/space/?userid=158898&yqcq.xml?feed_filter=20160910Mv1Ib.html
http://www.yqcq.gov.cn/e/space/?userid=158899&yqcq.xml?feed_filter=20160910By3Oy.html
http://www.yqcq.gov.cn/e/space/?userid=158900&yqcq.xml?feed_filter=20160910Ek7Vs.html
http://www.yqcq.gov.cn/e/space/?userid=158902&yqcq.xml?feed_filter=20160910Fd3Mi.html
http://www.yqcq.gov.cn/e/space/?userid=158903&yqcq.xml?feed_filter=20160910Ze9Ov.html
http://www.yqcq.gov.cn/e/space/?userid=158904&yqcq.xml?feed_filter=20160910Xa6Qf.html
http://www.yqcq.gov.cn/e/space/?userid=158905&yqcq.xml?feed_filter=20160910Cz9Jg.html
http://www.yqcq.gov.cn/e/space/?userid=158907&yqcq.xml?feed_filter=20160910Rj0Jd.html
http://www.yqcq.gov.cn/e/space/?userid=158908&yqcq.xml?feed_filter=20160910Sr5Ng.html
http://www.yqcq.gov.cn/e/space/?userid=158909&yqcq.xml?feed_filter=20160910Mk2Wd.html
http://www.yqcq.gov.cn/e/space/?userid=158910&yqcq.xml?feed_filter=20160910Za4Rh.html
http://www.yqcq.gov.cn/e/space/?userid=158912&yqcq.xml?feed_filter=20160910Lw8Zu.html
http://www.yqcq.gov.cn/e/space/?userid=158913&yqcq.xml?feed_filter=20160910Fu5Ms.html
http://www.yqcq.gov.cn/e/space/?userid=158914&yqcq.xml?feed_filter=20160910Uu0Xm.html
http://www.yqcq.gov.cn/e/space/?userid=158916&yqcq.xml?feed_filter=20160910Yt4Lq.html
http://www.yqcq.gov.cn/e/space/?userid=158917&yqcq.xml?feed_filter=20160910Mq7Wu.html
http://www.yqcq.gov.cn/e/space/?userid=158918&yqcq.xml?feed_filter=20160910Bg1Ht.html
http://www.yqcq.gov.cn/e/space/?userid=158920&yqcq.xml?feed_filter=20160910St2Iv.html
http://www.yqcq.gov.cn/e/space/?userid=158921&yqcq.xml?feed_filter=20160910Ux1Hg.html
http://www.yqcq.gov.cn/e/space/?userid=158922&yqcq.xml?feed_filter=20160910Kb3Od.html
http://www.yqcq.gov.cn/e/space/?userid=158923&yqcq.xml?feed_filter=20160910Tu8Hc.html
http://www.yqcq.gov.cn/e/space/?userid=158925&yqcq.xml?feed_filter=20160910Eg4Bx.html
http://www.yqcq.gov.cn/e/space/?userid=158926&yqcq.xml?feed_filter=20160910Fb6Yf.html
http://www.yqcq.gov.cn/e/space/?userid=158928&yqcq.xml?feed_filter=20160910Hw5Hs.html
http://www.yqcq.gov.cn/e/space/?userid=158931&yqcq.xml?feed_filter=20160910Dk7Oq.html
http://www.yqcq.gov.cn/e/space/?userid=158932&yqcq.xml?feed_filter=20160910Sv2Ki.html
http://www.yqcq.gov.cn/e/space/?userid=158933&yqcq.xml?feed_filter=20160910Lq8Zv.html
http://www.yqcq.gov.cn/e/space/?userid=158935&yqcq.xml?feed_filter=20160910Ka8Lt.html
http://www.yqcq.gov.cn/e/space/?userid=158937&yqcq.xml?feed_filter=20160910To3Er.html
http://www.yqcq.gov.cn/e/space/?userid=158938&yqcq.xml?feed_filter=20160910Hn6Im.html
http://www.yqcq.gov.cn/e/space/?userid=158940&yqcq.xml?feed_filter=20160910Uc8Ch.html
http://www.yqcq.gov.cn/e/space/?userid=158942&yqcq.xml?feed_filter=20160910Tf0Se.html
http://www.yqcq.gov.cn/e/space/?userid=158943&yqcq.xml?feed_filter=20160910Vh5Xv.html
http://www.yqcq.gov.cn/e/space/?userid=158944&yqcq.xml?feed_filter=20160910Un2Ja.html
http://www.yqcq.gov.cn/e/space/?userid=158946&yqcq.xml?feed_filter=20160910Xp6Fe.html
http://www.yqcq.gov.cn/e/space/?userid=158947&yqcq.xml?feed_filter=20160910Id7Vz.html
http://www.yqcq.gov.cn/e/space/?userid=158948&yqcq.xml?feed_filter=20160910Ha4Jc.html
http://www.yqcq.gov.cn/e/space/?userid=158950&yqcq.xml?feed_filter=20160910Dd7Nh.html
http://www.yqcq.gov.cn/e/space/?userid=158951&yqcq.xml?feed_filter=20160910Bq4Ly.html
http://www.yqcq.gov.cn/e/space/?userid=158952&yqcq.xml?feed_filter=20160910Fn8Cq.html
http://www.yqcq.gov.cn/e/space/?userid=158954&yqcq.xml?feed_filter=20160910Nt5Ut.html
http://www.yqcq.gov.cn/e/space/?userid=158955&yqcq.xml?feed_filter=20160910Ep3Ux.html
http://www.yqcq.gov.cn/e/space/?userid=158957&yqcq.xml?feed_filter=20160910Ur5Gg.html
http://www.yqcq.gov.cn/e/space/?userid=158958&yqcq.xml?feed_filter=20160910Wi7Xv.html
http://www.yqcq.gov.cn/e/space/?userid=158959&yqcq.xml?feed_filter=20160910Fr8Ld.html
http://www.yqcq.gov.cn/e/space/?userid=158961&yqcq.xml?feed_filter=20160910Gf7Yq.html
http://www.yqcq.gov.cn/e/space/?userid=158962&yqcq.xml?feed_filter=20160910Fp5Ne.html
http://www.yqcq.gov.cn/e/space/?userid=158963&yqcq.xml?feed_filter=20160910Dy5Ht.html
http://www.yqcq.gov.cn/e/space/?userid=158965&yqcq.xml?feed_filter=20160910Ui2Uv.html
http://www.yqcq.gov.cn/e/space/?userid=158966&yqcq.xml?feed_filter=20160910Og7Lb.html
http://www.yqcq.gov.cn/e/space/?userid=158967&yqcq.xml?feed_filter=20160910Kt7Rs.html
http://www.yqcq.gov.cn/e/space/?userid=158969&yqcq.xml?feed_filter=20160910Xj5Za.html
http://www.yqcq.gov.cn/e/space/?userid=158970&yqcq.xml?feed_filter=20160910Fy1Nl.html
http://www.yqcq.gov.cn/e/space/?userid=158971&yqcq.xml?feed_filter=20160910Jr7Ux.html
http://www.yqcq.gov.cn/e/space/?userid=158972&yqcq.xml?feed_filter=20160910Nt2Or.html
http://www.yqcq.gov.cn/e/space/?userid=158974&yqcq.xml?feed_filter=20160910Gi5Fn.html
http://www.yqcq.gov.cn/e/space/?userid=158975&yqcq.xml?feed_filter=20160910Wn9Dh.html
http://www.yqcq.gov.cn/e/space/?userid=158976&yqcq.xml?feed_filter=20160910Ua5Hu.html
http://www.yqcq.gov.cn/e/space/?userid=158977&yqcq.xml?feed_filter=20160910Sp2Qa.html
http://www.yqcq.gov.cn/e/space/?userid=158979&yqcq.xml?feed_filter=20160910Tm3Dw.html
http://www.yqcq.gov.cn/e/space/?userid=158980&yqcq.xml?feed_filter=20160910Dl9Ps.html
http://www.yqcq.gov.cn/e/space/?userid=158981&yqcq.xml?feed_filter=20160910Yq7Xc.html
http://www.yqcq.gov.cn/e/space/?userid=158983&yqcq.xml?feed_filter=20160910Zy3Ce.html
http://www.yqcq.gov.cn/e/space/?userid=158984&yqcq.xml?feed_filter=20160910Vn6Kh.html
http://www.yqcq.gov.cn/e/space/?userid=158985&yqcq.xml?feed_filter=20160910Bc4Bg.html
http://www.yqcq.gov.cn/e/space/?userid=158986&yqcq.xml?feed_filter=20160910Ok7Xm.html
http://www.yqcq.gov.cn/e/space/?userid=158988&yqcq.xml?feed_filter=20160910Gd2Bc.html
http://www.yqcq.gov.cn/e/space/?userid=158989&yqcq.xml?feed_filter=20160910Il9Jl.html
http://www.yqcq.gov.cn/e/space/?userid=158990&yqcq.xml?feed_filter=20160910Rp8Eq.html
http://www.yqcq.gov.cn/e/space/?userid=158991&yqcq.xml?feed_filter=20160910Iq0Nz.html
http://www.yqcq.gov.cn/e/space/?userid=158993&yqcq.xml?feed_filter=20160910Es3Qz.html
http://www.yqcq.gov.cn/e/space/?userid=158994&yqcq.xml?feed_filter=20160910Sr2Sn.html
http://www.yqcq.gov.cn/e/space/?userid=158995&yqcq.xml?feed_filter=20160910Zy1Tb.html
http://www.yqcq.gov.cn/e/space/?userid=158997&yqcq.xml?feed_filter=20160910Te0Tv.html
http://www.yqcq.gov.cn/e/space/?userid=158999&yqcq.xml?feed_filter=20160910Zt4Cs.html
http://www.yqcq.gov.cn/e/space/?userid=159000&yqcq.xml?feed_filter=20160910Gw9Wu.html
http://www.yqcq.gov.cn/e/space/?userid=159002&yqcq.xml?feed_filter=20160910Jp2Ux.html
http://www.yqcq.gov.cn/e/space/?userid=159003&yqcq.xml?feed_filter=20160910Dd4Wm.html
http://www.yqcq.gov.cn/e/space/?userid=159005&yqcq.xml?feed_filter=20160910Rf1Md.html
http://www.yqcq.gov.cn/e/space/?userid=159006&yqcq.xml?feed_filter=20160910Yi0Jm.html
http://www.yqcq.gov.cn/e/space/?userid=159007&yqcq.xml?feed_filter=20160910Ox8Ts.html
http://www.yqcq.gov.cn/e/space/?userid=159009&yqcq.xml?feed_filter=20160910Qx2Cn.html
http://www.yqcq.gov.cn/e/space/?userid=159010&yqcq.xml?feed_filter=20160910Ns4Jn.html
http://www.yqcq.gov.cn/e/space/?userid=159011&yqcq.xml?feed_filter=20160910Cd9Tf.html
http://www.yqcq.gov.cn/e/space/?userid=159013&yqcq.xml?feed_filter=20160910Xz9Yf.html
http://www.yqcq.gov.cn/e/space/?userid=159014&yqcq.xml?feed_filter=20160910Hy4Tj.html
http://www.yqcq.gov.cn/e/space/?userid=159015&yqcq.xml?feed_filter=20160910Eo7Li.html
http://www.yqcq.gov.cn/e/space/?userid=159016&yqcq.xml?feed_filter=20160910Uq4Pv.html
http://www.yqcq.gov.cn/e/space/?userid=159018&yqcq.xml?feed_filter=20160910Kd2Go.html
http://www.yqcq.gov.cn/e/space/?userid=159019&yqcq.xml?feed_filter=20160910Fu9Vg.html
http://www.yqcq.gov.cn/e/space/?userid=159020&yqcq.xml?feed_filter=20160910En9Ae.html
http://www.yqcq.gov.cn/e/space/?userid=159021&yqcq.xml?feed_filter=20160910We3At.html
http://www.yqcq.gov.cn/e/space/?userid=159024&yqcq.xml?feed_filter=20160910Do3Yf.html
http://www.yqcq.gov.cn/e/space/?userid=159025&yqcq.xml?feed_filter=20160910Kr6Mg.html
http://www.yqcq.gov.cn/e/space/?userid=159026&yqcq.xml?feed_filter=20160910Gj0Dg.html
http://www.yqcq.gov.cn/e/space/?userid=159028&yqcq.xml?feed_filter=20160910Ml3Gs.html
http://www.yqcq.gov.cn/e/space/?userid=159029&yqcq.xml?feed_filter=20160910Dm4Es.html
http://www.yqcq.gov.cn/e/space/?userid=159030&yqcq.xml?feed_filter=20160910Ax6Ua.html
http://www.yqcq.gov.cn/e/space/?userid=159031&yqcq.xml?feed_filter=20160910Fy3Rd.html
http://www.yqcq.gov.cn/e/space/?userid=159033&yqcq.xml?feed_filter=20160910Dt9Dc.html
http://www.yqcq.gov.cn/e/space/?userid=159034&yqcq.xml?feed_filter=20160910Sd0Hr.html
http://www.yqcq.gov.cn/e/space/?userid=159035&yqcq.xml?feed_filter=20160910Cl5Op.html
http://www.yqcq.gov.cn/e/space/?userid=159036&yqcq.xml?feed_filter=20160910Dt7Ah.html
http://www.yqcq.gov.cn/e/space/?userid=159037&yqcq.xml?feed_filter=20160910Hf9Gc.html
http://www.yqcq.gov.cn/e/space/?userid=159039&yqcq.xml?feed_filter=20160910Ju4Jk.html
http://www.yqcq.gov.cn/e/space/?userid=159040&yqcq.xml?feed_filter=20160910Tv7Wf.html
http://www.yqcq.gov.cn/e/space/?userid=159041&yqcq.xml?feed_filter=20160910Wx2Ma.html
http://www.yqcq.gov.cn/e/space/?userid=159043&yqcq.xml?feed_filter=20160910Nu1Kr.html
http://www.yqcq.gov.cn/e/space/?userid=159044&yqcq.xml?feed_filter=20160910Zq8Mg.html
http://www.yqcq.gov.cn/e/space/?userid=159045&yqcq.xml?feed_filter=20160910Zc6Fi.html
http://www.yqcq.gov.cn/e/space/?userid=159046&yqcq.xml?feed_filter=20160910Co0Sl.html
http://www.yqcq.gov.cn/e/space/?userid=159048&yqcq.xml?feed_filter=20160910Oe0Mz.html
http://www.yqcq.gov.cn/e/space/?userid=159049&yqcq.xml?feed_filter=20160910Af4Ut.html
http://www.yqcq.gov.cn/e/space/?userid=159050&yqcq.xml?feed_filter=20160910Ya7Qf.html
http://www.yqcq.gov.cn/e/space/?userid=159051&yqcq.xml?feed_filter=20160910Ce4Jf.html
http://www.yqcq.gov.cn/e/space/?userid=159053&yqcq.xml?feed_filter=20160910Qb5Pk.html
http://www.yqcq.gov.cn/e/space/?userid=159054&yqcq.xml?feed_filter=20160910Cd0Ni.html
http://www.yqcq.gov.cn/e/space/?userid=159055&yqcq.xml?feed_filter=20160910Rb7Zx.html
http://www.yqcq.gov.cn/e/space/?userid=159056&yqcq.xml?feed_filter=20160910Ny8Bc.html
http://www.yqcq.gov.cn/e/space/?userid=159058&yqcq.xml?feed_filter=20160910Nm2Ck.html
http://www.yqcq.gov.cn/e/space/?userid=159059&yqcq.xml?feed_filter=20160910Si4Fu.html
http://www.yqcq.gov.cn/e/space/?userid=159060&yqcq.xml?feed_filter=20160910Pb6Yi.html
http://www.yqcq.gov.cn/e/space/?userid=159061&yqcq.xml?feed_filter=20160910Ny0Mt.html
http://www.yqcq.gov.cn/e/space/?userid=159063&yqcq.xml?feed_filter=20160910Bu9Aa.html
http://www.yqcq.gov.cn/e/space/?userid=159064&yqcq.xml?feed_filter=20160910Lo4Nf.html
http://www.yqcq.gov.cn/e/space/?userid=159065&yqcq.xml?feed_filter=20160910Kq3Cg.html
http://www.yqcq.gov.cn/e/space/?userid=159066&yqcq.xml?feed_filter=20160910Xt8Hg.html
http://www.yqcq.gov.cn/e/space/?userid=159067&yqcq.xml?feed_filter=20160910Th1Rt.html
http://www.yqcq.gov.cn/e/space/?userid=159069&yqcq.xml?feed_filter=20160910Bn9Xd.html
http://www.yqcq.gov.cn/e/space/?userid=159070&yqcq.xml?feed_filter=20160910Hs9Jy.html
http://www.yqcq.gov.cn/e/space/?userid=159071&yqcq.xml?feed_filter=20160910Lc0Lp.html
http://www.yqcq.gov.cn/e/space/?userid=159073&yqcq.xml?feed_filter=20160910Ub7Ex.html
http://www.yqcq.gov.cn/e/space/?userid=159074&yqcq.xml?feed_filter=20160910Wa3Sz.html
http://www.yqcq.gov.cn/e/space/?userid=159075&yqcq.xml?feed_filter=20160910My0Jc.html
http://www.yqcq.gov.cn/e/space/?userid=159076&yqcq.xml?feed_filter=20160910Fn0Yq.html
http://www.yqcq.gov.cn/e/space/?userid=159078&yqcq.xml?feed_filter=20160910Hd1Lb.html
http://www.yqcq.gov.cn/e/space/?userid=159079&yqcq.xml?feed_filter=20160910Rj0Ko.html
http://www.yqcq.gov.cn/e/space/?userid=159080&yqcq.xml?feed_filter=20160910Pe8Ut.html
http://www.yqcq.gov.cn/e/space/?userid=159081&yqcq.xml?feed_filter=20160910Lk9Kf.html
http://www.yqcq.gov.cn/e/space/?userid=159083&yqcq.xml?feed_filter=20160910Km3Gu.html
http://www.yqcq.gov.cn/e/space/?userid=159084&yqcq.xml?feed_filter=20160910Ts7Zy.html
http://www.yqcq.gov.cn/e/space/?userid=159085&yqcq.xml?feed_filter=20160910Fd1Kw.html
http://www.yqcq.gov.cn/e/space/?userid=159086&yqcq.xml?feed_filter=20160910Ls5Oo.html
http://www.yqcq.gov.cn/e/space/?userid=159088&yqcq.xml?feed_filter=20160910Hm0Gq.html
http://www.yqcq.gov.cn/e/space/?userid=159089&yqcq.xml?feed_filter=20160910Es9Hr.html
http://www.yqcq.gov.cn/e/space/?userid=159090&yqcq.xml?feed_filter=20160910Np2Jl.html
http://www.yqcq.gov.cn/e/space/?userid=159092&yqcq.xml?feed_filter=20160910Lb3Zo.html
http://www.yqcq.gov.cn/e/space/?userid=159093&yqcq.xml?feed_filter=20160910Vd5Ep.html
http://www.yqcq.gov.cn/e/space/?userid=159094&yqcq.xml?feed_filter=20160910Gm6Od.html
http://www.yqcq.gov.cn/e/space/?userid=159096&yqcq.xml?feed_filter=20160910Da6Ue.html
http://www.yqcq.gov.cn/e/space/?userid=159097&yqcq.xml?feed_filter=20160910Me8Rb.html
http://www.yqcq.gov.cn/e/space/?userid=159099&yqcq.xml?feed_filter=20160910Cw0Iv.html
http://www.yqcq.gov.cn/e/space/?userid=159100&yqcq.xml?feed_filter=20160910Ua8Sx.html
http://www.yqcq.gov.cn/e/space/?userid=159101&yqcq.xml?feed_filter=20160910Hg7Js.html
http://www.yqcq.gov.cn/e/space/?userid=159103&yqcq.xml?feed_filter=20160910Cq6Qz.html
http://www.yqcq.gov.cn/e/space/?userid=159104&yqcq.xml?feed_filter=20160910Jy9Ub.html
http://www.yqcq.gov.cn/e/space/?userid=159105&yqcq.xml?feed_filter=20160910Bv2Iq.html
http://www.yqcq.gov.cn/e/space/?userid=159106&yqcq.xml?feed_filter=20160910Hn0Zc.html
http://www.yqcq.gov.cn/e/space/?userid=159108&yqcq.xml?feed_filter=20160910Is3Fv.html
http://www.yqcq.gov.cn/e/space/?userid=159109&yqcq.xml?feed_filter=20160910Jl1Xk.html
http://www.yqcq.gov.cn/e/space/?userid=159110&yqcq.xml?feed_filter=20160910Nv5Oh.html
http://www.yqcq.gov.cn/e/space/?userid=159112&yqcq.xml?feed_filter=20160910Xv7Rg.html
http://www.yqcq.gov.cn/e/space/?userid=159113&yqcq.xml?feed_filter=20160910Qn6Qo.html
http://www.yqcq.gov.cn/e/space/?userid=159114&yqcq.xml?feed_filter=20160910Qr1So.html
http://www.yqcq.gov.cn/e/space/?userid=159115&yqcq.xml?feed_filter=20160910Ko5Cu.html
http://www.yqcq.gov.cn/e/space/?userid=159117&yqcq.xml?feed_filter=20160910Nl6Pg.html
http://www.yqcq.gov.cn/e/space/?userid=159118&yqcq.xml?feed_filter=20160910Mg7Ag.html
http://www.yqcq.gov.cn/e/space/?userid=159119&yqcq.xml?feed_filter=20160910Yb7Ns.html
http://www.yqcq.gov.cn/e/space/?userid=159120&yqcq.xml?feed_filter=20160910Ph5Lt.html
http://www.yqcq.gov.cn/e/space/?userid=159122&yqcq.xml?feed_filter=20160910Yx9Lt.html
http://www.yqcq.gov.cn/e/space/?userid=159123&yqcq.xml?feed_filter=20160910Ji7Ox.html
http://www.yqcq.gov.cn/e/space/?userid=159124&yqcq.xml?feed_filter=20160910No5Lv.html
http://www.yqcq.gov.cn/e/space/?userid=159125&yqcq.xml?feed_filter=20160910Hx5Wx.html
http://www.yqcq.gov.cn/e/space/?userid=159127&yqcq.xml?feed_filter=20160910My2Mc.html
http://www.yqcq.gov.cn/e/space/?userid=159128&yqcq.xml?feed_filter=20160910Ap7Qa.html
http://www.yqcq.gov.cn/e/space/?userid=159129&yqcq.xml?feed_filter=20160910Mo4Ab.html
http://www.yqcq.gov.cn/e/space/?userid=159131&yqcq.xml?feed_filter=20160910Iz1Nc.html
http://www.yqcq.gov.cn/e/space/?userid=159132&yqcq.xml?feed_filter=20160910Zi7Yp.html
http://www.yqcq.gov.cn/e/space/?userid=159133&yqcq.xml?feed_filter=20160910Gv4Wm.html
http://www.yqcq.gov.cn/e/space/?userid=159134&yqcq.xml?feed_filter=20160910Aj8Uu.html
http://www.yqcq.gov.cn/e/space/?userid=159136&yqcq.xml?feed_filter=20160910Yq8Tb.html
http://www.yqcq.gov.cn/e/space/?userid=159137&yqcq.xml?feed_filter=20160910Cv3Dg.html
http://www.yqcq.gov.cn/e/space/?userid=159138&yqcq.xml?feed_filter=20160910Df5Zd.html
http://www.yqcq.gov.cn/e/space/?userid=159140&yqcq.xml?feed_filter=20160910Yc8Iu.html
http://www.yqcq.gov.cn/e/space/?userid=159142&yqcq.xml?feed_filter=20160910Qh5Bz.html
http://www.yqcq.gov.cn/e/space/?userid=159143&yqcq.xml?feed_filter=20160910Ah8Tc.html
http://www.yqcq.gov.cn/e/space/?userid=159144&yqcq.xml?feed_filter=20160910Nn5Ey.html
http://www.yqcq.gov.cn/e/space/?userid=159146&yqcq.xml?feed_filter=20160910Ka7Le.html
http://www.yqcq.gov.cn/e/space/?userid=159147&yqcq.xml?feed_filter=20160910Yz6Jg.html
http://www.yqcq.gov.cn/e/space/?userid=159148&yqcq.xml?feed_filter=20160910Ra5Ou.html
http://www.yqcq.gov.cn/e/space/?userid=159149&yqcq.xml?feed_filter=20160910Ci0Fh.html
http://www.yqcq.gov.cn/e/space/?userid=159151&yqcq.xml?feed_filter=20160910On3Zj.html
http://www.yqcq.gov.cn/e/space/?userid=159152&yqcq.xml?feed_filter=20160910Du5Ns.html
http://www.yqcq.gov.cn/e/space/?userid=159153&yqcq.xml?feed_filter=20160910Po0Ip.html
http://www.yqcq.gov.cn/e/space/?userid=159154&yqcq.xml?feed_filter=20160910Dz5Ig.html
http://www.yqcq.gov.cn/e/space/?userid=159156&yqcq.xml?feed_filter=20160910Hh4Mj.html
http://www.yqcq.gov.cn/e/space/?userid=159157&yqcq.xml?feed_filter=20160910Al8Ve.html
http://www.yqcq.gov.cn/e/space/?userid=159158&yqcq.xml?feed_filter=20160910Dq3Wi.html
http://www.yqcq.gov.cn/e/space/?userid=159160&yqcq.xml?feed_filter=20160910Pk7Yw.html
http://www.yqcq.gov.cn/e/space/?userid=159161&yqcq.xml?feed_filter=20160910Zj7Ob.html
http://www.yqcq.gov.cn/e/space/?userid=159162&yqcq.xml?feed_filter=20160910Lq3Es.html
http://www.yqcq.gov.cn/e/space/?userid=159163&yqcq.xml?feed_filter=20160910Ka6Gw.html
http://www.yqcq.gov.cn/e/space/?userid=159165&yqcq.xml?feed_filter=20160910Ah0Ge.html
http://www.yqcq.gov.cn/e/space/?userid=159166&yqcq.xml?feed_filter=20160910Ps9Xc.html
http://www.yqcq.gov.cn/e/space/?userid=159167&yqcq.xml?feed_filter=20160910Qd8Dn.html
http://www.yqcq.gov.cn/e/space/?userid=159169&yqcq.xml?feed_filter=20160910Kn3Za.html
http://www.yqcq.gov.cn/e/space/?userid=159170&yqcq.xml?feed_filter=20160910Vh2Ip.html
http://www.yqcq.gov.cn/e/space/?userid=159171&yqcq.xml?feed_filter=20160910Ml6Ny.html
http://www.yqcq.gov.cn/e/space/?userid=159173&yqcq.xml?feed_filter=20160910Lr4Oa.html
http://www.yqcq.gov.cn/e/space/?userid=159174&yqcq.xml?feed_filter=20160910Zn2Ug.html
http://www.yqcq.gov.cn/e/space/?userid=159175&yqcq.xml?feed_filter=20160910Mb6Ka.html
http://www.yqcq.gov.cn/e/space/?userid=159176&yqcq.xml?feed_filter=20160910Gl4Nh.html
http://www.yqcq.gov.cn/e/space/?userid=159178&yqcq.xml?feed_filter=20160910Ez3Uq.html
http://www.yqcq.gov.cn/e/space/?userid=159179&yqcq.xml?feed_filter=20160910Mu4Dk.html
http://www.yqcq.gov.cn/e/space/?userid=159180&yqcq.xml?feed_filter=20160910Tv1Pk.html
http://www.yqcq.gov.cn/e/space/?userid=159182&yqcq.xml?feed_filter=20160910Zx4Dz.html
http://www.yqcq.gov.cn/e/space/?userid=159183&yqcq.xml?feed_filter=20160910Nb9Fy.html
http://www.yqcq.gov.cn/e/space/?userid=159184&yqcq.xml?feed_filter=20160910Io3Sb.html
http://www.yqcq.gov.cn/e/space/?userid=159186&yqcq.xml?feed_filter=20160910Mr9Co.html
http://www.yqcq.gov.cn/e/space/?userid=159187&yqcq.xml?feed_filter=20160910Fa9Nj.html
http://www.yqcq.gov.cn/e/space/?userid=159188&yqcq.xml?feed_filter=20160910Ec9Pp.html
http://www.yqcq.gov.cn/e/space/?userid=159190&yqcq.xml?feed_filter=20160910Xt7Mi.html
http://www.yqcq.gov.cn/e/space/?userid=159191&yqcq.xml?feed_filter=20160910Rv8Za.html
http://www.yqcq.gov.cn/e/space/?userid=159192&yqcq.xml?feed_filter=20160910By7Yy.html
http://www.yqcq.gov.cn/e/space/?userid=159193&yqcq.xml?feed_filter=20160910Oi0Kw.html
http://www.yqcq.gov.cn/e/space/?userid=159195&yqcq.xml?feed_filter=20160910Sh7Rj.html
http://www.yqcq.gov.cn/e/space/?userid=159196&yqcq.xml?feed_filter=20160910Os2Mt.html
http://www.yqcq.gov.cn/e/space/?userid=159197&yqcq.xml?feed_filter=20160910Cf4Na.html
http://www.yqcq.gov.cn/e/space/?userid=159198&yqcq.xml?feed_filter=20160910Iz0Ot.html
http://www.yqcq.gov.cn/e/space/?userid=159200&yqcq.xml?feed_filter=20160910Rd0Ya.html
http://www.yqcq.gov.cn/e/space/?userid=159201&yqcq.xml?feed_filter=20160910En0Av.html
http://www.yqcq.gov.cn/e/space/?userid=159202&yqcq.xml?feed_filter=20160910Ls1Em.html
http://www.yqcq.gov.cn/e/space/?userid=159204&yqcq.xml?feed_filter=20160910Eq7Pm.html
http://www.yqcq.gov.cn/e/space/?userid=159205&yqcq.xml?feed_filter=20160910An8We.html
http://www.yqcq.gov.cn/e/space/?userid=159207&yqcq.xml?feed_filter=20160910Br3My.html
http://www.yqcq.gov.cn/e/space/?userid=159208&yqcq.xml?feed_filter=20160910Wy1Rg.html
http://www.yqcq.gov.cn/e/space/?userid=159210&yqcq.xml?feed_filter=20160910Me2Mk.html
http://www.yqcq.gov.cn/e/space/?userid=159211&yqcq.xml?feed_filter=20160910Se0Iy.html
http://www.yqcq.gov.cn/e/space/?userid=159213&yqcq.xml?feed_filter=20160910Os4Gn.html
http://www.yqcq.gov.cn/e/space/?userid=159214&yqcq.xml?feed_filter=20160910Pt4Rg.html
http://www.yqcq.gov.cn/e/space/?userid=159215&yqcq.xml?feed_filter=20160910Zw2Jl.html
http://www.yqcq.gov.cn/e/space/?userid=159217&yqcq.xml?feed_filter=20160910Ge5Le.html
http://www.yqcq.gov.cn/e/space/?userid=159218&yqcq.xml?feed_filter=20160910Ns9Gf.html
http://www.yqcq.gov.cn/e/space/?userid=159219&yqcq.xml?feed_filter=20160910Lz2Xm.html
http://www.yqcq.gov.cn/e/space/?userid=159220&yqcq.xml?feed_filter=20160910Ie3Hq.html
http://www.yqcq.gov.cn/e/space/?userid=159222&yqcq.xml?feed_filter=20160910Yh1Qa.html
http://www.yqcq.gov.cn/e/space/?userid=159224&yqcq.xml?feed_filter=20160910Sg2Xu.html
http://www.yqcq.gov.cn/e/space/?userid=159225&yqcq.xml?feed_filter=20160910Wf8Ra.html
http://www.yqcq.gov.cn/e/space/?userid=159227&yqcq.xml?feed_filter=20160910Fc6Yw.html
http://www.yqcq.gov.cn/e/space/?userid=159228&yqcq.xml?feed_filter=20160910Ib0Zb.html
http://www.yqcq.gov.cn/e/space/?userid=159229&yqcq.xml?feed_filter=20160910Za4Kx.html
http://www.yqcq.gov.cn/e/space/?userid=159231&yqcq.xml?feed_filter=20160910Lo5Bq.html
http://www.yqcq.gov.cn/e/space/?userid=159232&yqcq.xml?feed_filter=20160910Sc7Cd.html
http://www.yqcq.gov.cn/e/space/?userid=159233&yqcq.xml?feed_filter=20160910Sk8Js.html
http://www.yqcq.gov.cn/e/space/?userid=159235&yqcq.xml?feed_filter=20160910Qh3Vy.html
http://www.yqcq.gov.cn/e/space/?userid=159236&yqcq.xml?feed_filter=20160910Xg3Sd.html
http://www.yqcq.gov.cn/e/space/?userid=159237&yqcq.xml?feed_filter=20160910Of6Xr.html
http://www.yqcq.gov.cn/e/space/?userid=159238&yqcq.xml?feed_filter=20160910Wy0Tn.html
http://www.yqcq.gov.cn/e/space/?userid=159240&yqcq.xml?feed_filter=20160910Hc4Cz.html
http://www.yqcq.gov.cn/e/space/?userid=159242&yqcq.xml?feed_filter=20160910Md4Bd.html
http://www.yqcq.gov.cn/e/space/?userid=159244&yqcq.xml?feed_filter=20160910Sw0Px.html
http://www.yqcq.gov.cn/e/space/?userid=159245&yqcq.xml?feed_filter=20160910Wi9Jq.html
http://www.yqcq.gov.cn/e/space/?userid=159246&yqcq.xml?feed_filter=20160910Pr4Yt.html
http://www.yqcq.gov.cn/e/space/?userid=159248&yqcq.xml?feed_filter=20160910Ok1Sx.html
http://www.yqcq.gov.cn/e/space/?userid=159249&yqcq.xml?feed_filter=20160910Ob8Sp.html
http://www.yqcq.gov.cn/e/space/?userid=159250&yqcq.xml?feed_filter=20160910Vc1Fy.html
http://www.yqcq.gov.cn/e/space/?userid=159251&yqcq.xml?feed_filter=20160910Cc7Fx.html
http://www.yqcq.gov.cn/e/space/?userid=159252&yqcq.xml?feed_filter=20160910Tg5Cr.html
http://www.yqcq.gov.cn/e/space/?userid=159254&yqcq.xml?feed_filter=20160910Ug8Xp.html
http://www.yqcq.gov.cn/e/space/?userid=159255&yqcq.xml?feed_filter=20160910Bp9Oo.html
http://www.yqcq.gov.cn/e/space/?userid=159257&yqcq.xml?feed_filter=20160910Ey9Cn.html
http://www.yqcq.gov.cn/e/space/?userid=159258&yqcq.xml?feed_filter=20160910Ev8Vj.html
http://www.yqcq.gov.cn/e/space/?userid=159259&yqcq.xml?feed_filter=20160910Vu8Qb.html
http://www.yqcq.gov.cn/e/space/?userid=159261&yqcq.xml?feed_filter=20160910Kh8Qq.html
http://www.yqcq.gov.cn/e/space/?userid=159262&yqcq.xml?feed_filter=20160910Ao4Sh.html
http://www.yqcq.gov.cn/e/space/?userid=159264&yqcq.xml?feed_filter=20160910Ir4Jz.html
http://www.yqcq.gov.cn/e/space/?userid=159266&yqcq.xml?feed_filter=20160910Zm5Xz.html
http://www.yqcq.gov.cn/e/space/?userid=159267&yqcq.xml?feed_filter=20160910Xz4Uk.html
http://www.yqcq.gov.cn/e/space/?userid=159269&yqcq.xml?feed_filter=20160910Ro1Fr.html
http://www.yqcq.gov.cn/e/space/?userid=159270&yqcq.xml?feed_filter=20160910Aj2Hp.html
http://www.yqcq.gov.cn/e/space/?userid=159271&yqcq.xml?feed_filter=20160910Jy2Fr.html
http://www.yqcq.gov.cn/e/space/?userid=159273&yqcq.xml?feed_filter=20160910Zc9Xr.html
http://www.yqcq.gov.cn/e/space/?userid=159274&yqcq.xml?feed_filter=20160910Zy5Bx.html
http://www.yqcq.gov.cn/e/space/?userid=159275&yqcq.xml?feed_filter=20160910Ka7Uz.html
http://www.yqcq.gov.cn/e/space/?userid=159277&yqcq.xml?feed_filter=20160910Oj2Nk.html
http://www.yqcq.gov.cn/e/space/?userid=159278&yqcq.xml?feed_filter=20160910Ir9Oq.html
http://www.yqcq.gov.cn/e/space/?userid=159279&yqcq.xml?feed_filter=20160910Jj1Kv.html
http://www.yqcq.gov.cn/e/space/?userid=159281&yqcq.xml?feed_filter=20160910Ie9Ay.html
http://www.yqcq.gov.cn/e/space/?userid=159282&yqcq.xml?feed_filter=20160910Sr7Zu.html
http://www.yqcq.gov.cn/e/space/?userid=159283&yqcq.xml?feed_filter=20160910Kp7Et.html
http://www.yqcq.gov.cn/e/space/?userid=159284&yqcq.xml?feed_filter=20160910Ql3Es.html
http://www.yqcq.gov.cn/e/space/?userid=159285&yqcq.xml?feed_filter=20160910Hj0Vc.html
http://www.yqcq.gov.cn/e/space/?userid=159286&yqcq.xml?feed_filter=20160910Ts9Yo.html
http://www.yqcq.gov.cn/e/space/?userid=159287&yqcq.xml?feed_filter=20160910Yf0Ow.html
http://www.yqcq.gov.cn/e/space/?userid=159289&yqcq.xml?feed_filter=20160910We1Ra.html
http://www.yqcq.gov.cn/e/space/?userid=159290&yqcq.xml?feed_filter=20160910Tu3Fs.html
http://www.yqcq.gov.cn/e/space/?userid=159291&yqcq.xml?feed_filter=20160910Ee4Nf.html
http://www.yqcq.gov.cn/e/space/?userid=159292&yqcq.xml?feed_filter=20160910Bj0Te.html
http://www.yqcq.gov.cn/e/space/?userid=159294&yqcq.xml?feed_filter=20160910Fy8Fb.html
http://www.yqcq.gov.cn/e/space/?userid=159295&yqcq.xml?feed_filter=20160910Py9Ma.html
http://www.yqcq.gov.cn/e/space/?userid=159297&yqcq.xml?feed_filter=20160910Gl5Sl.html
http://www.yqcq.gov.cn/e/space/?userid=159298&yqcq.xml?feed_filter=20160910Bc4Fe.html
http://www.yqcq.gov.cn/e/space/?userid=159299&yqcq.xml?feed_filter=20160910Bx8Nq.html
http://www.yqcq.gov.cn/e/space/?userid=159300&yqcq.xml?feed_filter=20160910Or0Ay.html
http://www.yqcq.gov.cn/e/space/?userid=159302&yqcq.xml?feed_filter=20160910Bx3Rm.html
http://www.yqcq.gov.cn/e/space/?userid=159303&yqcq.xml?feed_filter=20160910Ux2Ka.html
http://www.yqcq.gov.cn/e/space/?userid=159304&yqcq.xml?feed_filter=20160910Hn0Ms.html
http://www.yqcq.gov.cn/e/space/?userid=159305&yqcq.xml?feed_filter=20160910Og8Gm.html
http://www.yqcq.gov.cn/e/space/?userid=159307&yqcq.xml?feed_filter=20160910Fr6At.html
http://www.yqcq.gov.cn/e/space/?userid=159308&yqcq.xml?feed_filter=20160910Xm2Lw.html
http://www.yqcq.gov.cn/e/space/?userid=159309&yqcq.xml?feed_filter=20160910Qr9Mj.html
http://www.yqcq.gov.cn/e/space/?userid=159310&yqcq.xml?feed_filter=20160910Rb6Ks.html
http://www.yqcq.gov.cn/e/space/?userid=159312&yqcq.xml?feed_filter=20160910Xj0It.html
http://www.yqcq.gov.cn/e/space/?userid=159313&yqcq.xml?feed_filter=20160910Pr0Kh.html
http://www.yqcq.gov.cn/e/space/?userid=159314&yqcq.xml?feed_filter=20160910Ou9Lp.html
http://www.yqcq.gov.cn/e/space/?userid=159316&yqcq.xml?feed_filter=20160910Ds4Yc.html
http://www.yqcq.gov.cn/e/space/?userid=159317&yqcq.xml?feed_filter=20160910Sn4Mw.html
http://www.yqcq.gov.cn/e/space/?userid=159318&yqcq.xml?feed_filter=20160910Ue8Ms.html
http://www.yqcq.gov.cn/e/space/?userid=159319&yqcq.xml?feed_filter=20160910Ei8Cf.html
http://www.yqcq.gov.cn/e/space/?userid=159321&yqcq.xml?feed_filter=20160910Bs7Nj.html
http://www.yqcq.gov.cn/e/space/?userid=159322&yqcq.xml?feed_filter=20160910Ku9Aq.html
http://www.yqcq.gov.cn/e/space/?userid=159323&yqcq.xml?feed_filter=20160910Tw0Ir.html
http://www.yqcq.gov.cn/e/space/?userid=159324&yqcq.xml?feed_filter=20160910Gd9Se.html
http://www.yqcq.gov.cn/e/space/?userid=159326&yqcq.xml?feed_filter=20160910Qq4Wx.html
http://www.yqcq.gov.cn/e/space/?userid=159327&yqcq.xml?feed_filter=20160910Xp9Hl.html
http://www.yqcq.gov.cn/e/space/?userid=159328&yqcq.xml?feed_filter=20160910Ic1Ei.html
http://www.yqcq.gov.cn/e/space/?userid=159330&yqcq.xml?feed_filter=20160910Os0Pg.html
http://www.yqcq.gov.cn/e/space/?userid=159331&yqcq.xml?feed_filter=20160910Rw9Hx.html
http://www.yqcq.gov.cn/e/space/?userid=159333&yqcq.xml?feed_filter=20160910Cq6Ze.html
http://www.yqcq.gov.cn/e/space/?userid=159334&yqcq.xml?feed_filter=20160910La5Ao.html
http://www.yqcq.gov.cn/e/space/?userid=159335&yqcq.xml?feed_filter=20160910Id7Tc.html
http://www.yqcq.gov.cn/e/space/?userid=159337&yqcq.xml?feed_filter=20160910Qs2Eh.html
http://www.yqcq.gov.cn/e/space/?userid=159338&yqcq.xml?feed_filter=20160910Es5Oo.html
http://www.yqcq.gov.cn/e/space/?userid=159339&yqcq.xml?feed_filter=20160910Tj9Sm.html
http://www.yqcq.gov.cn/e/space/?userid=159341&yqcq.xml?feed_filter=20160910Er4Fu.html
http://www.yqcq.gov.cn/e/space/?userid=159342&yqcq.xml?feed_filter=20160910Bz8Oz.html
http://www.yqcq.gov.cn/e/space/?userid=159343&yqcq.xml?feed_filter=20160910Ht7Mu.html
http://www.yqcq.gov.cn/e/space/?userid=159345&yqcq.xml?feed_filter=20160910Tq5Ry.html
http://www.yqcq.gov.cn/e/space/?userid=159347&yqcq.xml?feed_filter=20160910Sr7Oa.html
http://www.yqcq.gov.cn/e/space/?userid=159348&yqcq.xml?feed_filter=20160910Lg6Mz.html
http://www.yqcq.gov.cn/e/space/?userid=159349&yqcq.xml?feed_filter=20160910Jz8Zw.html
http://www.yqcq.gov.cn/e/space/?userid=159351&yqcq.xml?feed_filter=20160910Bv9Su.html
http://www.yqcq.gov.cn/e/space/?userid=159352&yqcq.xml?feed_filter=20160910Xj4Uf.html
http://www.yqcq.gov.cn/e/space/?userid=159353&yqcq.xml?feed_filter=20160910Op8Ob.html
http://www.yqcq.gov.cn/e/space/?userid=159355&yqcq.xml?feed_filter=20160910Xz9Hk.html
http://www.yqcq.gov.cn/e/space/?userid=159356&yqcq.xml?feed_filter=20160910Nm3Of.html
http://www.yqcq.gov.cn/e/space/?userid=159357&yqcq.xml?feed_filter=20160910Rd8Fa.html
http://www.yqcq.gov.cn/e/space/?userid=159359&yqcq.xml?feed_filter=20160910Zi8Hp.html
http://www.yqcq.gov.cn/e/space/?userid=159360&yqcq.xml?feed_filter=20160910Eq4Jt.html
http://www.yqcq.gov.cn/e/space/?userid=159361&yqcq.xml?feed_filter=20160910Mh5Ri.html
http://www.yqcq.gov.cn/e/space/?userid=159363&yqcq.xml?feed_filter=20160910Iy5Oo.html
http://www.yqcq.gov.cn/e/space/?userid=159364&yqcq.xml?feed_filter=20160910Lw6Vc.html
http://www.yqcq.gov.cn/e/space/?userid=159365&yqcq.xml?feed_filter=20160910Gn5Rl.html
http://www.yqcq.gov.cn/e/space/?userid=159367&yqcq.xml?feed_filter=20160910Tl5Vj.html
http://www.yqcq.gov.cn/e/space/?userid=159368&yqcq.xml?feed_filter=20160910Vc2Sk.html
http://www.yqcq.gov.cn/e/space/?userid=159369&yqcq.xml?feed_filter=20160910Ee8Cw.html
http://www.yqcq.gov.cn/e/space/?userid=159371&yqcq.xml?feed_filter=20160910Ld7Yx.html
http://www.yqcq.gov.cn/e/space/?userid=159373&yqcq.xml?feed_filter=20160910Rz4Nc.html
http://www.yqcq.gov.cn/e/space/?userid=159374&yqcq.xml?feed_filter=20160910Dy4Jv.html
http://www.yqcq.gov.cn/e/space/?userid=159375&yqcq.xml?feed_filter=20160910Yq8Ht.html
http://www.yqcq.gov.cn/e/space/?userid=159376&yqcq.xml?feed_filter=20160910Gv3Wq.html
http://www.yqcq.gov.cn/e/space/?userid=159377&yqcq.xml?feed_filter=20160910Rb8Bc.html
http://www.yqcq.gov.cn/e/space/?userid=159379&yqcq.xml?feed_filter=20160910Ul5Nq.html
http://www.yqcq.gov.cn/e/space/?userid=159380&yqcq.xml?feed_filter=20160910Ho8Fu.html
http://www.yqcq.gov.cn/e/space/?userid=159381&yqcq.xml?feed_filter=20160910Fa6Ni.html
http://www.yqcq.gov.cn/e/space/?userid=159383&yqcq.xml?feed_filter=20160910Es9Km.html
http://www.yqcq.gov.cn/e/space/?userid=159384&yqcq.xml?feed_filter=20160910Fe5Vj.html
http://www.yqcq.gov.cn/e/space/?userid=159385&yqcq.xml?feed_filter=20160910At1Cm.html
http://www.yqcq.gov.cn/e/space/?userid=159386&yqcq.xml?feed_filter=20160910Nc9Tx.html
http://www.yqcq.gov.cn/e/space/?userid=159388&yqcq.xml?feed_filter=20160910Pd8Nc.html
http://www.yqcq.gov.cn/e/space/?userid=159389&yqcq.xml?feed_filter=20160910Fg7Fz.html
http://www.yqcq.gov.cn/e/space/?userid=159390&yqcq.xml?feed_filter=20160910Ik6Cl.html
http://www.yqcq.gov.cn/e/space/?userid=159391&yqcq.xml?feed_filter=20160910Bm5Ck.html
http://www.yqcq.gov.cn/e/space/?userid=159392&yqcq.xml?feed_filter=20160910Ia0Gu.html
http://www.yqcq.gov.cn/e/space/?userid=159394&yqcq.xml?feed_filter=20160910Ee5Co.html
http://www.yqcq.gov.cn/e/space/?userid=159395&yqcq.xml?feed_filter=20160910Ir9Mg.html
http://www.yqcq.gov.cn/e/space/?userid=159397&yqcq.xml?feed_filter=20160910Rm7Uz.html
http://www.yqcq.gov.cn/e/space/?userid=159398&yqcq.xml?feed_filter=20160910Mv7Ht.html
http://www.yqcq.gov.cn/e/space/?userid=159400&yqcq.xml?feed_filter=20160910Qt9Jc.html
http://www.yqcq.gov.cn/e/space/?userid=159401&yqcq.xml?feed_filter=20160910Wm6Bw.html
http://www.yqcq.gov.cn/e/space/?userid=159403&yqcq.xml?feed_filter=20160910Fy1Mc.html
http://www.yqcq.gov.cn/e/space/?userid=159404&yqcq.xml?feed_filter=20160910Jq0Wu.html
http://www.yqcq.gov.cn/e/space/?userid=159405&yqcq.xml?feed_filter=20160910Hl3Kc.html
http://www.yqcq.gov.cn/e/space/?userid=159406&yqcq.xml?feed_filter=20160910Kq8St.html
http://www.yqcq.gov.cn/e/space/?userid=159408&yqcq.xml?feed_filter=20160910Pn4Yz.html
http://www.yqcq.gov.cn/e/space/?userid=159409&yqcq.xml?feed_filter=20160910Ni8At.html
http://www.yqcq.gov.cn/e/space/?userid=159410&yqcq.xml?feed_filter=20160910Ak9Dd.html
http://www.yqcq.gov.cn/e/space/?userid=159411&yqcq.xml?feed_filter=20160910Ns8Wz.html
http://www.yqcq.gov.cn/e/space/?userid=159413&yqcq.xml?feed_filter=20160910Ba6Wo.html
http://www.yqcq.gov.cn/e/space/?userid=159414&yqcq.xml?feed_filter=20160910Pw7Gc.html
http://www.yqcq.gov.cn/e/space/?userid=159416&yqcq.xml?feed_filter=20160910Wv9Zr.html
http://www.yqcq.gov.cn/e/space/?userid=159417&yqcq.xml?feed_filter=20160910Xu4Ga.html
http://www.yqcq.gov.cn/e/space/?userid=159418&yqcq.xml?feed_filter=20160910Zj5Td.html
http://www.yqcq.gov.cn/e/space/?userid=159419&yqcq.xml?feed_filter=20160910Km9Pc.html
http://www.yqcq.gov.cn/e/space/?userid=159421&yqcq.xml?feed_filter=20160910Zc2Vb.html
http://www.yqcq.gov.cn/e/space/?userid=159422&yqcq.xml?feed_filter=20160910Fm2Nf.html
http://www.yqcq.gov.cn/e/space/?userid=159423&yqcq.xml?feed_filter=20160910Td0Wj.html
http://www.yqcq.gov.cn/e/space/?userid=159426&yqcq.xml?feed_filter=20160910Yv2Fe.html
http://www.yqcq.gov.cn/e/space/?userid=159427&yqcq.xml?feed_filter=20160910Mm0Jz.html
http://www.yqcq.gov.cn/e/space/?userid=159429&yqcq.xml?feed_filter=20160910Mp3Rt.html
http://www.yqcq.gov.cn/e/space/?userid=159430&yqcq.xml?feed_filter=20160910Kw8Be.html
http://www.yqcq.gov.cn/e/space/?userid=159431&yqcq.xml?feed_filter=20160910Ru9Em.html
http://www.yqcq.gov.cn/e/space/?userid=159432&yqcq.xml?feed_filter=20160910Vi6Nv.html
http://www.yqcq.gov.cn/e/space/?userid=159434&yqcq.xml?feed_filter=20160910Gk8Vy.html
http://www.yqcq.gov.cn/e/space/?userid=159435&yqcq.xml?feed_filter=20160910Zu7Rh.html
http://www.yqcq.gov.cn/e/space/?userid=159437&yqcq.xml?feed_filter=20160910Ij7Zg.html
http://www.yqcq.gov.cn/e/space/?userid=159438&yqcq.xml?feed_filter=20160910Ko7Cs.html
http://www.yqcq.gov.cn/e/space/?userid=159440&yqcq.xml?feed_filter=20160910Hh9Fz.html
http://www.yqcq.gov.cn/e/space/?userid=159441&yqcq.xml?feed_filter=20160910Me7Vn.html
http://www.yqcq.gov.cn/e/space/?userid=159443&yqcq.xml?feed_filter=20160910Ak6Ih.html
http://www.yqcq.gov.cn/e/space/?userid=159444&yqcq.xml?feed_filter=20160910Do5Xp.html
http://www.yqcq.gov.cn/e/space/?userid=159445&yqcq.xml?feed_filter=20160910No0Hn.html
http://www.yqcq.gov.cn/e/space/?userid=159447&yqcq.xml?feed_filter=20160910Hf3Vq.html
http://www.yqcq.gov.cn/e/space/?userid=159448&yqcq.xml?feed_filter=20160910Tp5Ct.html
http://www.yqcq.gov.cn/e/space/?userid=159509&yqcq.xml?feed_filter=20160910Ko3Io.html
http://www.yqcq.gov.cn/e/space/?userid=159511&yqcq.xml?feed_filter=20160910Ih7Yo.html
http://www.yqcq.gov.cn/e/space/?userid=159512&yqcq.xml?feed_filter=20160910Sz2Sq.html
http://www.yqcq.gov.cn/e/space/?userid=159514&yqcq.xml?feed_filter=20160910Le3Qv.html
http://www.yqcq.gov.cn/e/space/?userid=159515&yqcq.xml?feed_filter=20160910Zc9Px.html
http://www.yqcq.gov.cn/e/space/?userid=159516&yqcq.xml?feed_filter=20160910Ba7Ju.html
http://www.yqcq.gov.cn/e/space/?userid=159518&yqcq.xml?feed_filter=20160910Gk9Rw.html
http://www.yqcq.gov.cn/e/space/?userid=159519&yqcq.xml?feed_filter=20160910Mc0Jv.html
http://www.yqcq.gov.cn/e/space/?userid=159520&yqcq.xml?feed_filter=20160910Ko6Gx.html
http://www.yqcq.gov.cn/e/space/?userid=159521&yqcq.xml?feed_filter=20160910Ss0Wi.html
http://www.yqcq.gov.cn/e/space/?userid=159523&yqcq.xml?feed_filter=20160910Jv7Yi.html
http://www.yqcq.gov.cn/e/space/?userid=159524&yqcq.xml?feed_filter=20160910En1Lf.html
http://www.yqcq.gov.cn/e/space/?userid=159525&yqcq.xml?feed_filter=20160910Lq5Ra.html
http://www.yqcq.gov.cn/e/space/?userid=159527&yqcq.xml?feed_filter=20160910Ng1Tr.html
http://www.yqcq.gov.cn/e/space/?userid=159528&yqcq.xml?feed_filter=20160910Us0Ax.html
http://www.yqcq.gov.cn/e/space/?userid=159529&yqcq.xml?feed_filter=20160910Ka7Uy.html
http://www.yqcq.gov.cn/e/space/?userid=159530&yqcq.xml?feed_filter=20160910Xw1Lz.html
http://www.yqcq.gov.cn/e/space/?userid=159531&yqcq.xml?feed_filter=20160910Mz3Dq.html
http://www.yqcq.gov.cn/e/space/?userid=159533&yqcq.xml?feed_filter=20160910Uq4Dj.html
http://www.yqcq.gov.cn/e/space/?userid=159534&yqcq.xml?feed_filter=20160910At1Qm.html
http://www.yqcq.gov.cn/e/space/?userid=159535&yqcq.xml?feed_filter=20160910Lx8Oh.html
http://www.yqcq.gov.cn/e/space/?userid=159536&yqcq.xml?feed_filter=20160910Hw9Xr.html
http://www.yqcq.gov.cn/e/space/?userid=159538&yqcq.xml?feed_filter=20160910Ta6Vq.html
http://www.yqcq.gov.cn/e/space/?userid=159539&yqcq.xml?feed_filter=20160910Oq8Al.html
http://www.yqcq.gov.cn/e/space/?userid=159540&yqcq.xml?feed_filter=20160910Gg8Yg.html
http://www.yqcq.gov.cn/e/space/?userid=159541&yqcq.xml?feed_filter=20160910Se3Vw.html
http://www.yqcq.gov.cn/e/space/?userid=159543&yqcq.xml?feed_filter=20160910Xk7Jv.html
http://www.yqcq.gov.cn/e/space/?userid=159544&yqcq.xml?feed_filter=20160910Ho6Sr.html
http://www.yqcq.gov.cn/e/space/?userid=159545&yqcq.xml?feed_filter=20160910Xx6Js.html
http://www.yqcq.gov.cn/e/space/?userid=159546&yqcq.xml?feed_filter=20160910Xf0Vu.html
http://www.yqcq.gov.cn/e/space/?userid=159548&yqcq.xml?feed_filter=20160910Ty3Gn.html
http://www.yqcq.gov.cn/e/space/?userid=159549&yqcq.xml?feed_filter=20160910Ak2Cl.html
http://www.yqcq.gov.cn/e/space/?userid=159550&yqcq.xml?feed_filter=20160910Js0Pk.html
http://www.yqcq.gov.cn/e/space/?userid=159551&yqcq.xml?feed_filter=20160910Ja8Zm.html
http://www.yqcq.gov.cn/e/space/?userid=159552&yqcq.xml?feed_filter=20160910Uw9Su.html
http://www.yqcq.gov.cn/e/space/?userid=159554&yqcq.xml?feed_filter=20160910Ha9Bg.html
http://www.yqcq.gov.cn/e/space/?userid=159555&yqcq.xml?feed_filter=20160910Vs4Uk.html
http://www.yqcq.gov.cn/e/space/?userid=159556&yqcq.xml?feed_filter=20160910Ut7Qu.html
http://www.yqcq.gov.cn/e/space/?userid=159558&yqcq.xml?feed_filter=20160910Up9Zo.html
http://www.yqcq.gov.cn/e/space/?userid=159559&yqcq.xml?feed_filter=20160910Qq3Oa.html
http://www.yqcq.gov.cn/e/space/?userid=159560&yqcq.xml?feed_filter=20160910Pa0Lm.html
http://www.yqcq.gov.cn/e/space/?userid=159561&yqcq.xml?feed_filter=20160910Bm8Dm.html
http://www.yqcq.gov.cn/e/space/?userid=159563&yqcq.xml?feed_filter=20160910Rk7Qi.html
http://www.yqcq.gov.cn/e/space/?userid=159564&yqcq.xml?feed_filter=20160910Iu0Dg.html
http://www.yqcq.gov.cn/e/space/?userid=159565&yqcq.xml?feed_filter=20160910Oi2Ym.html
http://www.yqcq.gov.cn/e/space/?userid=159566&yqcq.xml?feed_filter=20160910Xu2Lb.html
http://www.yqcq.gov.cn/e/space/?userid=159568&yqcq.xml?feed_filter=20160910Wk9Ep.html
http://www.yqcq.gov.cn/e/space/?userid=159569&yqcq.xml?feed_filter=20160910Et9Kw.html
http://www.yqcq.gov.cn/e/space/?userid=159570&yqcq.xml?feed_filter=20160910Gm8Gq.html
http://www.yqcq.gov.cn/e/space/?userid=159571&yqcq.xml?feed_filter=20160910Ms5Yp.html
http://www.yqcq.gov.cn/e/space/?userid=159573&yqcq.xml?feed_filter=20160910Xt7Nd.html
http://www.yqcq.gov.cn/e/space/?userid=159574&yqcq.xml?feed_filter=20160910Ki2Ik.html
http://www.yqcq.gov.cn/e/space/?userid=159575&yqcq.xml?feed_filter=20160910Rn5Ho.html
http://www.yqcq.gov.cn/e/space/?userid=159576&yqcq.xml?feed_filter=20160910Ec1Qr.html
http://www.yqcq.gov.cn/e/space/?userid=159578&yqcq.xml?feed_filter=20160910Gz1Nh.html
http://www.yqcq.gov.cn/e/space/?userid=159579&yqcq.xml?feed_filter=20160910Oe7Mu.html
http://www.yqcq.gov.cn/e/space/?userid=159580&yqcq.xml?feed_filter=20160910Ag0Jx.html
http://www.yqcq.gov.cn/e/space/?userid=159581&yqcq.xml?feed_filter=20160910Fj9Oi.html
http://www.yqcq.gov.cn/e/space/?userid=159582&yqcq.xml?feed_filter=20160910Vp0Lr.html
http://www.yqcq.gov.cn/e/space/?userid=159584&yqcq.xml?feed_filter=20160910Nz0Km.html
http://www.yqcq.gov.cn/e/space/?userid=159585&yqcq.xml?feed_filter=20160910Gz9Nd.html
http://www.yqcq.gov.cn/e/space/?userid=159586&yqcq.xml?feed_filter=20160910Qj8Qs.html
http://www.yqcq.gov.cn/e/space/?userid=159587&yqcq.xml?feed_filter=20160910It2Er.html
http://www.yqcq.gov.cn/e/space/?userid=159589&yqcq.xml?feed_filter=20160910Uv5Du.html
http://www.yqcq.gov.cn/e/space/?userid=159590&yqcq.xml?feed_filter=20160910Nh2Iz.html
http://www.yqcq.gov.cn/e/space/?userid=159591&yqcq.xml?feed_filter=20160910Qm8Jp.html
http://www.yqcq.gov.cn/e/space/?userid=159593&yqcq.xml?feed_filter=20160910Ja9Oq.html
http://www.yqcq.gov.cn/e/space/?userid=159594&yqcq.xml?feed_filter=20160910Hd0Lv.html
http://www.yqcq.gov.cn/e/space/?userid=159595&yqcq.xml?feed_filter=20160910Wk2Dg.html
http://www.yqcq.gov.cn/e/space/?userid=159596&yqcq.xml?feed_filter=20160910Pi3Yo.html
http://www.yqcq.gov.cn/e/space/?userid=159598&yqcq.xml?feed_filter=20160910Jk8Dx.html
http://www.yqcq.gov.cn/e/space/?userid=159599&yqcq.xml?feed_filter=20160910Eo0Cp.html
http://www.yqcq.gov.cn/e/space/?userid=159600&yqcq.xml?feed_filter=20160910Ty1Eq.html
http://www.yqcq.gov.cn/e/space/?userid=159601&yqcq.xml?feed_filter=20160910Kv6Dy.html
http://www.yqcq.gov.cn/e/space/?userid=159603&yqcq.xml?feed_filter=20160910Pz4Ou.html
http://www.yqcq.gov.cn/e/space/?userid=159604&yqcq.xml?feed_filter=20160910Se9Xw.html
http://www.yqcq.gov.cn/e/space/?userid=159605&yqcq.xml?feed_filter=20160910Ew4Vh.html
http://www.yqcq.gov.cn/e/space/?userid=159606&yqcq.xml?feed_filter=20160910Kz2Wz.html
http://www.yqcq.gov.cn/e/space/?userid=159608&yqcq.xml?feed_filter=20160910Bt9Yh.html
http://www.yqcq.gov.cn/e/space/?userid=159609&yqcq.xml?feed_filter=20160910Kz8Fz.html
http://www.yqcq.gov.cn/e/space/?userid=159610&yqcq.xml?feed_filter=20160910Jb6Qx.html
http://www.yqcq.gov.cn/e/space/?userid=159611&yqcq.xml?feed_filter=20160910Vt3Yr.html
http://www.yqcq.gov.cn/e/space/?userid=159613&yqcq.xml?feed_filter=20160910By8Fv.html
http://www.yqcq.gov.cn/e/space/?userid=159614&yqcq.xml?feed_filter=20160910Uu5Mj.html
http://www.yqcq.gov.cn/e/space/?userid=159615&yqcq.xml?feed_filter=20160910Ot7Ar.html
http://www.yqcq.gov.cn/e/space/?userid=159617&yqcq.xml?feed_filter=20160910Rb3Fz.html
http://www.yqcq.gov.cn/e/space/?userid=159618&yqcq.xml?feed_filter=20160910As0Xz.html
http://www.yqcq.gov.cn/e/space/?userid=159619&yqcq.xml?feed_filter=20160910Kn5Mi.html
http://www.yqcq.gov.cn/e/space/?userid=159620&yqcq.xml?feed_filter=20160910Rw3Eo.html
http://www.yqcq.gov.cn/e/space/?userid=159622&yqcq.xml?feed_filter=20160910Mp3Ng.html
http://www.yqcq.gov.cn/e/space/?userid=159623&yqcq.xml?feed_filter=20160910My2Hv.html
http://www.yqcq.gov.cn/e/space/?userid=159624&yqcq.xml?feed_filter=20160910Vj7Jj.html
http://www.yqcq.gov.cn/e/space/?userid=159625&yqcq.xml?feed_filter=20160910Zb1Md.html
http://www.yqcq.gov.cn/e/space/?userid=159627&yqcq.xml?feed_filter=20160910Jq0Ua.html
http://www.yqcq.gov.cn/e/space/?userid=159628&yqcq.xml?feed_filter=20160910Gk7Wz.html
http://www.yqcq.gov.cn/e/space/?userid=159629&yqcq.xml?feed_filter=20160910Op0Ts.html
http://www.yqcq.gov.cn/e/space/?userid=159630&yqcq.xml?feed_filter=20160910Qf0Ni.html
http://www.yqcq.gov.cn/e/space/?userid=159632&yqcq.xml?feed_filter=20160910Dv6Ar.html
http://www.yqcq.gov.cn/e/space/?userid=159633&yqcq.xml?feed_filter=20160910Nj2Wx.html
http://www.yqcq.gov.cn/e/space/?userid=159634&yqcq.xml?feed_filter=20160910Dz7Wx.html
http://www.yqcq.gov.cn/e/space/?userid=159635&yqcq.xml?feed_filter=20160910Io2Ab.html
http://www.yqcq.gov.cn/e/space/?userid=159637&yqcq.xml?feed_filter=20160910Fs3Xm.html
http://www.yqcq.gov.cn/e/space/?userid=159638&yqcq.xml?feed_filter=20160910Bn9Vl.html
http://www.yqcq.gov.cn/e/space/?userid=159639&yqcq.xml?feed_filter=20160910Cv9Jg.html
http://www.yqcq.gov.cn/e/space/?userid=159640&yqcq.xml?feed_filter=20160910Ya1Dh.html
http://www.yqcq.gov.cn/e/space/?userid=159642&yqcq.xml?feed_filter=20160910Bc6Mb.html
http://www.yqcq.gov.cn/e/space/?userid=159643&yqcq.xml?feed_filter=20160910Ce5Ab.html
http://www.yqcq.gov.cn/e/space/?userid=159644&yqcq.xml?feed_filter=20160910Bq8Ul.html
http://www.yqcq.gov.cn/e/space/?userid=159646&yqcq.xml?feed_filter=20160910Bg8Ye.html
http://www.yqcq.gov.cn/e/space/?userid=159647&yqcq.xml?feed_filter=20160910Db0Bt.html
http://www.yqcq.gov.cn/e/space/?userid=159649&yqcq.xml?feed_filter=20160910Lm0Qz.html
http://www.yqcq.gov.cn/e/space/?userid=159650&yqcq.xml?feed_filter=20160910Cr1To.html
http://www.yqcq.gov.cn/e/space/?userid=159652&yqcq.xml?feed_filter=20160910Fl6Rd.html
http://www.yqcq.gov.cn/e/space/?userid=159653&yqcq.xml?feed_filter=20160910Ot3Jv.html
http://www.yqcq.gov.cn/e/space/?userid=159654&yqcq.xml?feed_filter=20160910Hf8Fk.html
http://www.yqcq.gov.cn/e/space/?userid=159656&yqcq.xml?feed_filter=20160910Fk3Na.html
http://www.yqcq.gov.cn/e/space/?userid=159657&yqcq.xml?feed_filter=20160910Lf5Tg.html
http://www.yqcq.gov.cn/e/space/?userid=159659&yqcq.xml?feed_filter=20160910Cr6Rx.html
http://www.yqcq.gov.cn/e/space/?userid=159660&yqcq.xml?feed_filter=20160910Sx2Zl.html
http://www.yqcq.gov.cn/e/space/?userid=159662&yqcq.xml?feed_filter=20160910Ud0Bl.html
http://www.yqcq.gov.cn/e/space/?userid=159663&yqcq.xml?feed_filter=20160910Du9Rp.html
http://www.yqcq.gov.cn/e/space/?userid=159665&yqcq.xml?feed_filter=20160910Qg3Bz.html
http://www.yqcq.gov.cn/e/space/?userid=159666&yqcq.xml?feed_filter=20160910Ql7Vq.html
http://www.yqcq.gov.cn/e/space/?userid=159667&yqcq.xml?feed_filter=20160910Gq8Fs.html
http://www.yqcq.gov.cn/e/space/?userid=159668&yqcq.xml?feed_filter=20160910Bv1Na.html
http://www.yqcq.gov.cn/e/space/?userid=159670&yqcq.xml?feed_filter=20160910Ur6Dz.html
http://www.yqcq.gov.cn/e/space/?userid=159671&yqcq.xml?feed_filter=20160910Ep7Iw.html
http://www.yqcq.gov.cn/e/space/?userid=159672&yqcq.xml?feed_filter=20160910Gy6Zz.html
http://www.yqcq.gov.cn/e/space/?userid=159674&yqcq.xml?feed_filter=20160910Jv1Wd.html
http://www.yqcq.gov.cn/e/space/?userid=159675&yqcq.xml?feed_filter=20160910Oq2Az.html
http://www.yqcq.gov.cn/e/space/?userid=159676&yqcq.xml?feed_filter=20160910Ey9In.html
http://www.yqcq.gov.cn/e/space/?userid=159678&yqcq.xml?feed_filter=20160910Ec4Oe.html
http://www.yqcq.gov.cn/e/space/?userid=159679&yqcq.xml?feed_filter=20160910Zu2Je.html
http://www.yqcq.gov.cn/e/space/?userid=159681&yqcq.xml?feed_filter=20160910Gr0Pd.html
http://www.yqcq.gov.cn/e/space/?userid=159683&yqcq.xml?feed_filter=20160910Up8Jx.html
http://www.yqcq.gov.cn/e/space/?userid=159684&yqcq.xml?feed_filter=20160910Tv2Zo.html
http://www.yqcq.gov.cn/e/space/?userid=159685&yqcq.xml?feed_filter=20160910Vo7Qc.html
http://www.yqcq.gov.cn/e/space/?userid=159687&yqcq.xml?feed_filter=20160910Sw8Yn.html
http://www.yqcq.gov.cn/e/space/?userid=159689&yqcq.xml?feed_filter=20160910Gc4Kl.html
http://www.yqcq.gov.cn/e/space/?userid=159690&yqcq.xml?feed_filter=20160910Hv6Sy.html
http://www.yqcq.gov.cn/e/space/?userid=159692&yqcq.xml?feed_filter=20160910Em7Zd.html
http://www.yqcq.gov.cn/e/space/?userid=159693&yqcq.xml?feed_filter=20160910Ac4Ja.html
http://www.yqcq.gov.cn/e/space/?userid=159694&yqcq.xml?feed_filter=20160910Yf5Xk.html
http://www.yqcq.gov.cn/e/space/?userid=159695&yqcq.xml?feed_filter=20160910Gu0Uh.html
http://www.yqcq.gov.cn/e/space/?userid=159696&yqcq.xml?feed_filter=20160910Wb3Sy.html
http://www.yqcq.gov.cn/e/space/?userid=159698&yqcq.xml?feed_filter=20160910Jc9Yb.html
http://www.yqcq.gov.cn/e/space/?userid=159699&yqcq.xml?feed_filter=20160910Mo5Fm.html
http://www.yqcq.gov.cn/e/space/?userid=159701&yqcq.xml?feed_filter=20160910Pv0Jr.html
http://www.yqcq.gov.cn/e/space/?userid=159702&yqcq.xml?feed_filter=20160910Xh0Ei.html
http://www.yqcq.gov.cn/e/space/?userid=159703&yqcq.xml?feed_filter=20160910Da8Qk.html
http://www.yqcq.gov.cn/e/space/?userid=159704&yqcq.xml?feed_filter=20160910Po9Tz.html
http://www.yqcq.gov.cn/e/space/?userid=159706&yqcq.xml?feed_filter=20160910Lh3Du.html
http://www.yqcq.gov.cn/e/space/?userid=159707&yqcq.xml?feed_filter=20160910Ma7Gr.html
http://www.yqcq.gov.cn/e/space/?userid=159708&yqcq.xml?feed_filter=20160910Fz9Mx.html
http://www.yqcq.gov.cn/e/space/?userid=159710&yqcq.xml?feed_filter=20160910Ou0Ds.html
http://www.yqcq.gov.cn/e/space/?userid=159711&yqcq.xml?feed_filter=20160910Kw5Hc.html
http://www.yqcq.gov.cn/e/space/?userid=159712&yqcq.xml?feed_filter=20160910Op0Id.html
http://www.yqcq.gov.cn/e/space/?userid=159714&yqcq.xml?feed_filter=20160910Yl4Dj.html
http://www.yqcq.gov.cn/e/space/?userid=159715&yqcq.xml?feed_filter=20160910Jq6Ne.html
http://www.yqcq.gov.cn/e/space/?userid=159716&yqcq.xml?feed_filter=20160910Gy1Wo.html
http://www.yqcq.gov.cn/e/space/?userid=159718&yqcq.xml?feed_filter=20160910Zn7Zb.html
http://www.yqcq.gov.cn/e/space/?userid=159719&yqcq.xml?feed_filter=20160910Ow8Pf.html
http://www.yqcq.gov.cn/e/space/?userid=159720&yqcq.xml?feed_filter=20160910Sl0Yn.html
http://www.yqcq.gov.cn/e/space/?userid=159722&yqcq.xml?feed_filter=20160910Ay7Zz.html
http://www.yqcq.gov.cn/e/space/?userid=159723&yqcq.xml?feed_filter=20160910Cc3Fp.html
http://www.yqcq.gov.cn/e/space/?userid=159724&yqcq.xml?feed_filter=20160910Bl2Gp.html
http://www.yqcq.gov.cn/e/space/?userid=159726&yqcq.xml?feed_filter=20160910Yg4Lh.html
http://www.yqcq.gov.cn/e/space/?userid=159727&yqcq.xml?feed_filter=20160910Te0Hz.html
http://www.yqcq.gov.cn/e/space/?userid=159728&yqcq.xml?feed_filter=20160910Ro1Qd.html
http://www.yqcq.gov.cn/e/space/?userid=159729&yqcq.xml?feed_filter=20160910Zx2Tz.html
http://www.yqcq.gov.cn/e/space/?userid=159731&yqcq.xml?feed_filter=20160910Rh6Sh.html
http://www.yqcq.gov.cn/e/space/?userid=159732&yqcq.xml?feed_filter=20160910Ld3Tb.html
http://www.yqcq.gov.cn/e/space/?userid=159733&yqcq.xml?feed_filter=20160910Ux9Qn.html
http://www.yqcq.gov.cn/e/space/?userid=159734&yqcq.xml?feed_filter=20160910Ll8Cw.html
http://www.yqcq.gov.cn/e/space/?userid=159736&yqcq.xml?feed_filter=20160910Qi9Vc.html
http://www.yqcq.gov.cn/e/space/?userid=159737&yqcq.xml?feed_filter=20160910Ek5Gt.html
http://www.yqcq.gov.cn/e/space/?userid=159738&yqcq.xml?feed_filter=20160910Px1Rr.html
http://www.yqcq.gov.cn/e/space/?userid=159739&yqcq.xml?feed_filter=20160910Gs8Aq.html
http://www.yqcq.gov.cn/e/space/?userid=159740&yqcq.xml?feed_filter=20160910Ch0Nu.html
http://www.yqcq.gov.cn/e/space/?userid=159742&yqcq.xml?feed_filter=20160910Zd1Sz.html
http://www.yqcq.gov.cn/e/space/?userid=159743&yqcq.xml?feed_filter=20160910Aq0Pf.html
http://www.yqcq.gov.cn/e/space/?userid=159744&yqcq.xml?feed_filter=20160910Uj0Uo.html
http://www.yqcq.gov.cn/e/space/?userid=159745&yqcq.xml?feed_filter=20160910Tz0Fi.html
http://www.yqcq.gov.cn/e/space/?userid=159746&yqcq.xml?feed_filter=20160910Py6Mj.html
http://www.yqcq.gov.cn/e/space/?userid=159748&yqcq.xml?feed_filter=20160910Zo8Nk.html
http://www.yqcq.gov.cn/e/space/?userid=159749&yqcq.xml?feed_filter=20160910Yb4Mz.html
http://www.yqcq.gov.cn/e/space/?userid=159750&yqcq.xml?feed_filter=20160910Fp5Vk.html
http://www.yqcq.gov.cn/e/space/?userid=159751&yqcq.xml?feed_filter=20160910Qi6Ih.html
http://www.yqcq.gov.cn/e/space/?userid=159753&yqcq.xml?feed_filter=20160910Lk8Fu.html
http://www.yqcq.gov.cn/e/space/?userid=159754&yqcq.xml?feed_filter=20160910Ta4At.html
http://www.yqcq.gov.cn/e/space/?userid=159755&yqcq.xml?feed_filter=20160910Px1Fa.html
http://www.yqcq.gov.cn/e/space/?userid=159756&yqcq.xml?feed_filter=20160910Oo8Il.html
http://www.yqcq.gov.cn/e/space/?userid=159757&yqcq.xml?feed_filter=20160910Wp9Gk.html
http://www.yqcq.gov.cn/e/space/?userid=159759&yqcq.xml?feed_filter=20160910Tz5Fq.html
http://www.yqcq.gov.cn/e/space/?userid=159760&yqcq.xml?feed_filter=20160910Uw2Sf.html
http://www.yqcq.gov.cn/e/space/?userid=159761&yqcq.xml?feed_filter=20160910Au7Rq.html
http://www.yqcq.gov.cn/e/space/?userid=159762&yqcq.xml?feed_filter=20160910Qf7Gj.html
http://www.yqcq.gov.cn/e/space/?userid=159764&yqcq.xml?feed_filter=20160910Yu8Pn.html
http://www.yqcq.gov.cn/e/space/?userid=159765&yqcq.xml?feed_filter=20160910Wn1By.html
http://www.yqcq.gov.cn/e/space/?userid=159766&yqcq.xml?feed_filter=20160910Dg9Iu.html
http://www.yqcq.gov.cn/e/space/?userid=159768&yqcq.xml?feed_filter=20160910Oa0Fj.html
http://www.yqcq.gov.cn/e/space/?userid=159769&yqcq.xml?feed_filter=20160910Gd9Qt.html
http://www.yqcq.gov.cn/e/space/?userid=159770&yqcq.xml?feed_filter=20160910Bm5Op.html
http://www.yqcq.gov.cn/e/space/?userid=159771&yqcq.xml?feed_filter=20160910Vm0Vj.html
http://www.yqcq.gov.cn/e/space/?userid=159772&yqcq.xml?feed_filter=20160910Zd5Ng.html
http://www.yqcq.gov.cn/e/space/?userid=159774&yqcq.xml?feed_filter=20160910Sz9Yg.html
http://www.yqcq.gov.cn/e/space/?userid=159775&yqcq.xml?feed_filter=20160910Md8Jm.html
http://www.yqcq.gov.cn/e/space/?userid=159776&yqcq.xml?feed_filter=20160910Gl6Mc.html
http://www.yqcq.gov.cn/e/space/?userid=159777&yqcq.xml?feed_filter=20160910Bh9Qa.html
http://www.yqcq.gov.cn/e/space/?userid=159779&yqcq.xml?feed_filter=20160910Nr2Fa.html
http://www.yqcq.gov.cn/e/space/?userid=159780&yqcq.xml?feed_filter=20160910Rv3Vq.html
http://www.yqcq.gov.cn/e/space/?userid=159781&yqcq.xml?feed_filter=20160910Jo2Wa.html
http://www.yqcq.gov.cn/e/space/?userid=159782&yqcq.xml?feed_filter=20160910Do8Ao.html
http://www.yqcq.gov.cn/e/space/?userid=159784&yqcq.xml?feed_filter=20160910Kb2Li.html
http://www.yqcq.gov.cn/e/space/?userid=159785&yqcq.xml?feed_filter=20160910Ve6Js.html
http://www.yqcq.gov.cn/e/space/?userid=159786&yqcq.xml?feed_filter=20160910Pe5Ql.html
http://www.yqcq.gov.cn/e/space/?userid=159787&yqcq.xml?feed_filter=20160910Zt2En.html
http://www.yqcq.gov.cn/e/space/?userid=159789&yqcq.xml?feed_filter=20160910Vo4Rf.html
http://www.yqcq.gov.cn/e/space/?userid=159790&yqcq.xml?feed_filter=20160910Jo1Pk.html
http://www.yqcq.gov.cn/e/space/?userid=159791&yqcq.xml?feed_filter=20160910Yr2Gg.html
http://www.yqcq.gov.cn/e/space/?userid=159792&yqcq.xml?feed_filter=20160910Rw4Wk.html
http://www.yqcq.gov.cn/e/space/?userid=159794&yqcq.xml?feed_filter=20160910Ga9Nn.html
http://www.yqcq.gov.cn/e/space/?userid=159795&yqcq.xml?feed_filter=20160910Ub3Ra.html
http://www.yqcq.gov.cn/e/space/?userid=159796&yqcq.xml?feed_filter=20160910Ul5Dq.html
http://www.yqcq.gov.cn/e/space/?userid=159797&yqcq.xml?feed_filter=20160910Ab7Hn.html
http://www.yqcq.gov.cn/e/space/?userid=159799&yqcq.xml?feed_filter=20160910En9Ci.html
http://www.yqcq.gov.cn/e/space/?userid=159800&yqcq.xml?feed_filter=20160910Jv7Yi.html
http://www.yqcq.gov.cn/e/space/?userid=159801&yqcq.xml?feed_filter=20160910Wx4Jk.html
http://www.yqcq.gov.cn/e/space/?userid=159802&yqcq.xml?feed_filter=20160910Rb1Dc.html
http://www.yqcq.gov.cn/e/space/?userid=159804&yqcq.xml?feed_filter=20160910Hh0Zf.html
http://www.yqcq.gov.cn/e/space/?userid=159805&yqcq.xml?feed_filter=20160910Dk8Ne.html
http://www.yqcq.gov.cn/e/space/?userid=159806&yqcq.xml?feed_filter=20160910Fs2Sz.html
http://www.yqcq.gov.cn/e/space/?userid=159808&yqcq.xml?feed_filter=20160910Dr8Ac.html
http://www.yqcq.gov.cn/e/space/?userid=159809&yqcq.xml?feed_filter=20160910Wq5Gf.html
http://www.yqcq.gov.cn/e/space/?userid=159810&yqcq.xml?feed_filter=20160910Bz0Ik.html
http://www.yqcq.gov.cn/e/space/?userid=159811&yqcq.xml?feed_filter=20160910Dy7Zi.html
http://www.yqcq.gov.cn/e/space/?userid=159812&yqcq.xml?feed_filter=20160910Kx5Ib.html
http://www.yqcq.gov.cn/e/space/?userid=159814&yqcq.xml?feed_filter=20160910Vw7Nm.html
http://www.yqcq.gov.cn/e/space/?userid=159815&yqcq.xml?feed_filter=20160910Dq7Nf.html
http://www.yqcq.gov.cn/e/space/?userid=159816&yqcq.xml?feed_filter=20160910Ch4Ff.html
http://www.yqcq.gov.cn/e/space/?userid=159817&yqcq.xml?feed_filter=20160910Qx6Fa.html
http://www.yqcq.gov.cn/e/space/?userid=159819&yqcq.xml?feed_filter=20160910Ey0Xu.html
http://www.yqcq.gov.cn/e/space/?userid=159820&yqcq.xml?feed_filter=20160910Rs3Lb.html
http://www.yqcq.gov.cn/e/space/?userid=159821&yqcq.xml?feed_filter=20160910Te7Xb.html
http://www.yqcq.gov.cn/e/space/?userid=159822&yqcq.xml?feed_filter=20160910Vk1Lt.html
http://www.yqcq.gov.cn/e/space/?userid=159824&yqcq.xml?feed_filter=20160910Xu6Gk.html
http://www.yqcq.gov.cn/e/space/?userid=159825&yqcq.xml?feed_filter=20160910Cv5Fe.html
http://www.yqcq.gov.cn/e/space/?userid=159826&yqcq.xml?feed_filter=20160910Vx4Iu.html
http://www.yqcq.gov.cn/e/space/?userid=159827&yqcq.xml?feed_filter=20160910Wf8Fr.html
http://www.yqcq.gov.cn/e/space/?userid=159829&yqcq.xml?feed_filter=20160910Ec0Lo.html
http://www.yqcq.gov.cn/e/space/?userid=159830&yqcq.xml?feed_filter=20160910Zj6Lb.html
http://www.yqcq.gov.cn/e/space/?userid=159831&yqcq.xml?feed_filter=20160910Iz1Lh.html
http://www.yqcq.gov.cn/e/space/?userid=159833&yqcq.xml?feed_filter=20160910Ii9Pf.html
http://www.yqcq.gov.cn/e/space/?userid=159834&yqcq.xml?feed_filter=20160910Td3Zr.html
http://www.yqcq.gov.cn/e/space/?userid=159836&yqcq.xml?feed_filter=20160910Is2Pf.html
http://www.yqcq.gov.cn/e/space/?userid=159837&yqcq.xml?feed_filter=20160910Bz4Nc.html
http://www.yqcq.gov.cn/e/space/?userid=159838&yqcq.xml?feed_filter=20160910Lx8Lk.html
http://www.yqcq.gov.cn/e/space/?userid=159840&yqcq.xml?feed_filter=20160910Vg1Hy.html
http://www.yqcq.gov.cn/e/space/?userid=159841&yqcq.xml?feed_filter=20160910Ns6Ac.html
http://www.yqcq.gov.cn/e/space/?userid=159843&yqcq.xml?feed_filter=20160910Wb7Ct.html
http://www.yqcq.gov.cn/e/space/?userid=159844&yqcq.xml?feed_filter=20160910Wr6Wd.html
http://www.yqcq.gov.cn/e/space/?userid=159846&yqcq.xml?feed_filter=20160910Kh6Aa.html
http://www.yqcq.gov.cn/e/space/?userid=159847&yqcq.xml?feed_filter=20160910Nx4Vq.html
http://www.yqcq.gov.cn/e/space/?userid=159848&yqcq.xml?feed_filter=20160910Rn9Nn.html
http://www.yqcq.gov.cn/e/space/?userid=159850&yqcq.xml?feed_filter=20160910Jt4Bj.html
http://www.yqcq.gov.cn/e/space/?userid=159851&yqcq.xml?feed_filter=20160910Tj3Xy.html
http://www.yqcq.gov.cn/e/space/?userid=159852&yqcq.xml?feed_filter=20160910Qm8Qy.html
http://www.yqcq.gov.cn/e/space/?userid=159854&yqcq.xml?feed_filter=20160910Je2Gx.html
http://www.yqcq.gov.cn/e/space/?userid=159855&yqcq.xml?feed_filter=20160910Av8Sy.html
http://www.yqcq.gov.cn/e/space/?userid=159856&yqcq.xml?feed_filter=20160910My3Xx.html
http://www.yqcq.gov.cn/e/space/?userid=159857&yqcq.xml?feed_filter=20160910Hn8Pp.html
http://www.yqcq.gov.cn/e/space/?userid=159859&yqcq.xml?feed_filter=20160910Lp7Jm.html
http://www.yqcq.gov.cn/e/space/?userid=159860&yqcq.xml?feed_filter=20160910Qb4Cp.html
http://www.yqcq.gov.cn/e/space/?userid=159861&yqcq.xml?feed_filter=20160910Xe0Si.html
http://www.yqcq.gov.cn/e/space/?userid=159862&yqcq.xml?feed_filter=20160910Br2Br.html
http://www.yqcq.gov.cn/e/space/?userid=159864&yqcq.xml?feed_filter=20160910Dq3Jc.html
http://www.yqcq.gov.cn/e/space/?userid=159865&yqcq.xml?feed_filter=20160910Oe1Ol.html


这个函数作用就类似 ES6 里面的 rest params ,这个函数主要是在官网分类里面的 collections 用到,例如: invoke 。

主要原理是利用回调函数来处理调用方法传入的参数。

创建继承函数

var baseCreate = function(prototype) {
    if (!_.isObject(prototype)) return {};
    if (nativeCreate) return nativeCreate(prototype);
    Ctor.prototype = prototype;
    var result = new Ctor;
    // 创建 result 之后清空 Ctor 的原型链,防止 全局变量 Ctor 的原型链污染
    Ctor.prototype = null;
    return result;
  };

主要原理就是利用 Ctor 做一个中介,创建继承函数并返回后再清空Ctor的原型链,防止原型链污染

取对象的属性值

var property = function(key) {
    return function(obj) {
      return obj == null ? void 0 : obj[key];
    };
  };

这个方法浅显易懂,如果传入的 object 为 null ,则返回 undefined ,否则返回属性值。

其它的全局变量

var MAX_ARRAY_INDEX = Math.pow(2, 53) - 1;
var getLength = property('length');
var isArrayLike = function(collection) {
  var length = getLength(collection);
  return typeof length == 'number' && length >= 0 && length <= MAX_ARRAY_INDEX;
  };

主要是帮助 collection 的方法来判定某个变量是否为 collection 。

作者:fwlhy1216 发表于2016/9/10 23:13:50 原文链接
阅读:46 评论:0 查看评论

工作中遇到的Android内存优化问题(3)-leakcanary源码解析

$
0
0

今天我们来看一下一个内存泄漏检测神器 leakcanary(https://github.com/square/leakcanary)

首先我们来看一下leakcanary的使用说明


就这么多,只需要一行代码,太简单了,简单得都有点怀疑它了。

我们来看一下一个简单的例子,也是它官方源码中提供的一个例子,这个因为太小了我就截了个图


从例子中可以看到,AsyncTask执行了sleep操作,但是由于AsyncTask声明为了一个内部匿名类,此类持有外部类的对象,导致用户退出此Activity时,此Activity不能被gc回收,安装此例子到手机,点击START NEW ASYNCTASK,退出app,观察手机,会弹出一个内存泄漏通知如下图



很神奇吧,连泄漏的堆栈调用信息都能查到,比我们在前两篇用到的工具方便多了


leakcanary很神奇,就像魔术一样,我们很想知道它背后的运行机制,现在我们就来解析一下leakcanary的源码。首先从我们应用Application入手,因为leakcanary在使用中只有一行代码,我们就从这行代码慢慢跟踪一下源码。

public class ExampleApplication extends Application {

  @Override public void onCreate() {
    super.onCreate();
    LeakCanary.install(this);
  }
}

首先我们进入install方法,install方法调用了另一个install方法

  public static RefWatcher install(Application application) {
    return install(application, DisplayLeakService.class,
        AndroidExcludedRefs.createAppDefaults().build());
  }


  /**
   * Creates a {@link RefWatcher} that reports results to the provided service, and starts watching
   * activity references (on ICS+).
   */
  public static RefWatcher install(Application application,
                                   Class<? extends AbstractAnalysisResultService> listenerServiceClass,
                                   ExcludedRefs excludedRefs) {
    if (isInAnalyzerProcess(application)) {
      return RefWatcher.DISABLED;
    }
    enableDisplayLeakActivity(application);
    //此Listener很重要,在后面会扮演重要角色
    HeapDump.Listener heapDumpListener =
            new ServiceHeapDumpListener(application, listenerServiceClass);
    //从名字我们就可以看出它是监视内存泄漏对象的
    RefWatcher refWatcher = androidWatcher(application, heapDumpListener, excludedRefs);
    //
    ActivityRefWatcher.installOnIcsPlus(application, refWatcher);
    return refWatcher;
  }



接着进入installOnIcsPlus方法,此方法就到了关键的地方,能解开为什么我们只用一个方法,就能监听所有的内存泄漏

  public static void installOnIcsPlus(Application application, RefWatcher refWatcher) {
    if (SDK_INT < ICE_CREAM_SANDWICH) {
      // If you need to support Android < ICS, override onDestroy() in your base activity.
      return;
    }
    ActivityRefWatcher activityRefWatcher = new ActivityRefWatcher(application, refWatcher);
    activityRefWatcher.watchActivities();
  }


 ActivityRefWtacher提供了一个方法 watchActivitys()

  public void watchActivities() {
    // Make sure you don't get installed twice.
    stopWatchingActivities();
    application.registerActivityLifecycleCallbacks(lifecycleCallbacks);
  }

Android4.0以上的Application中提供了registerActivityLifecycleCallbacks方法,此方法从名字就可以看出是监听Activity生命周期的,我们再来看看参数lifecycleCallbacks的定义,

  private final Application.ActivityLifecycleCallbacks lifecycleCallbacks =
      new Application.ActivityLifecycleCallbacks() {
        @Override public void onActivityCreated(Activity activity, Bundle savedInstanceState) {
        }

        @Override public void onActivityStarted(Activity activity) {
        }

        @Override public void onActivityResumed(Activity activity) {
        }

        @Override public void onActivityPaused(Activity activity) {
        }

        @Override public void onActivityStopped(Activity activity) {
        }

        @Override public void onActivitySaveInstanceState(Activity activity, Bundle outState) {
        }

        @Override public void onActivityDestroyed(Activity activity) {
          ActivityRefWatcher.this.onActivityDestroyed(activity);
        }
      };

看到了吧,所有Activity们只要调用了onDestroy方法,就会被回调方法onActivityDestroyed知道,然后传入 ActivityRefWatcher的方法 onActivityDestroyed中,此方法很简单

  void onActivityDestroyed(Activity activity) {
    refWatcher.watch(activity);
  }

refWatcher就是我们上面install方法中创建的,进入watch方法

 public void watch(Object watchedReference, String referenceName) {
    checkNotNull(watchedReference, "watchedReference");
    checkNotNull(referenceName, "referenceName");
    if (debuggerControl.isDebuggerAttached()) {
      return;
    }
    final long watchStartNanoTime = System.nanoTime();
    //首先生成了一个id,此id是用来唯一标识这个检测对象的
    String key = UUID.randomUUID().toString();
    //将id存起来
    retainedKeys.add(key);
    //KeyWeakReference集成自 WeakReference(弱引用),WeakReference使用来跟踪这个对象的,
    //弱引用大家都明白,它不会影响gc回收,构造WeakReference时,可以传入一个ReferenceQueue,
    //这个ReferenceQueue的主要作用是当对象不可达时也就是可以被gc回收时,对象所对应的WeakReference就会被放入
    //ReferenceQueue中,只要检测ReferenceQueue是否有我们的对象的WeakReference,就可以判断对象是否可能泄漏
    final KeyedWeakReference reference =
        new KeyedWeakReference(watchedReference, key, referenceName, queue);

    watchExecutor.execute(new Runnable() {
      @Override public void run() {
        //此方法就是为了确认对象是否可回收
        ensureGone(reference, watchStartNanoTime);
      }
    });
  }

进入ensureGone方法

void ensureGone(KeyedWeakReference reference, long watchStartNanoTime) {
    long gcStartNanoTime = System.nanoTime();

    long watchDurationMs = NANOSECONDS.toMillis(gcStartNanoTime - watchStartNanoTime);
    //此方法是循环ReferenceQueue,如果对象的ReferenceQueue在里面,就从retainedKeys中移除对象的key,
    //因为此对象已经可回收,是安全的
    removeWeaklyReachableReferences();
    //判断我们要检测的reference是否还在retainedKeys中,如果不在说明已经被移除了,也就是可以被gc回收了
    if (gone(reference) || debuggerControl.isDebuggerAttached()) {
      return;
    }
    //执行垃圾回收,但是只是建议,并不是一定会执行
    gcTrigger.runGc();
    //再次从retainedKeys移除安全的key
    removeWeaklyReachableReferences();
    //如果此对象的WeakReference还是不能被回收,那么此对象就有可能泄漏了,只是可能,因为gc在上一步可能没有运行
    if (!gone(reference)) {
      long startDumpHeap = System.nanoTime();
      long gcDurationMs = NANOSECONDS.toMillis(startDumpHeap - gcStartNanoTime);
      //此方法获得内存Heap的hprof文件,LeakCanary之所以这么好用,主要是在这里,它分析了hprof文件,来确认内存泄漏,
      //我们在上一篇也分析过hprof文件,原来LeakCanary也是分析这个文件,只是不需要人工分析了,LeakCanary用了一个自己
      //的开源hprof分析库haha(https://github.com/square/haha)此库是基于google的perflib.
      File heapDumpFile = heapDumper.dumpHeap();

      if (heapDumpFile == HeapDumper.NO_DUMP) {
        // Could not dump the heap, abort.
        return;
      }
      long heapDumpDurationMs = NANOSECONDS.toMillis(System.nanoTime() - startDumpHeap);
      //heapdumpListener主要就是启动服务分析hprof文件
      heapdumpListener.analyze(
          new HeapDump(heapDumpFile, reference.key, reference.name, excludedRefs, watchDurationMs,
              gcDurationMs, heapDumpDurationMs));
    }
  }

heapdumpListener在前面创建的时候是一个ServiceHeapDumpListener对象,进入此对象的analyze方法

  @Override public void analyze(HeapDump heapDump) {
    checkNotNull(heapDump, "heapDump");
    HeapAnalyzerService.runAnalysis(context, heapDump, listenerServiceClass);
  }

  public static void runAnalysis(Context context, HeapDump heapDump,
      Class<? extends AbstractAnalysisResultService> listenerServiceClass) {
    Intent intent = new Intent(context, HeapAnalyzerService.class);
    intent.putExtra(LISTENER_CLASS_EXTRA, listenerServiceClass.getName());
    intent.putExtra(HEAPDUMP_EXTRA, heapDump);
    context.startService(intent);
  }

启动服务分析hprof文件,接着我们来看看这个服务

  @Override protected void onHandleIntent(Intent intent) {
    if (intent == null) {
      CanaryLog.d("HeapAnalyzerService received a null intent, ignoring.");
      return;
    }
    String listenerClassName = intent.getStringExtra(LISTENER_CLASS_EXTRA);
    HeapDump heapDump = (HeapDump) intent.getSerializableExtra(HEAPDUMP_EXTRA);

    //分析hprof的核心类
    HeapAnalyzer heapAnalyzer = new HeapAnalyzer(heapDump.excludedRefs);
    //检查我们的对象是否内存泄漏
    AnalysisResult result = heapAnalyzer.checkForLeak(heapDump.heapDumpFile, heapDump.referenceKey);
    AbstractAnalysisResultService.sendResultToListener(this, listenerClassName, heapDump, result);
  }
进入checkForLeak方法
 public AnalysisResult checkForLeak(File heapDumpFile, String referenceKey) {
    long analysisStartNanoTime = System.nanoTime();

    if (!heapDumpFile.exists()) {
      Exception exception = new IllegalArgumentException("File does not exist: " + heapDumpFile);
      return failure(exception, since(analysisStartNanoTime));
    }

    try {
      HprofBuffer buffer = new MemoryMappedFileBuffer(heapDumpFile);
      //解析器解析文件
      HprofParser parser = new HprofParser(buffer);
      //解析过程,是基于google的perflib库,根据hprof的格式进行解析,这里就不展开看了
      Snapshot snapshot = parser.parse();
      //分析结果进行去重
      deduplicateGcRoots(snapshot);
      //此方法就是根据我们需要检测的类的key,查询解析结果中是否有我们的对象,获取解析结果中我们检测的对象
      Instance leakingRef = findLeakingReference(referenceKey, snapshot);
      //此对象不存在表示已经被gc清除了,不存在泄露因此返回无泄漏
      // False alarm, weak reference was cleared in between key check and heap dump.
      if (leakingRef == null) {
        return noLeak(since(analysisStartNanoTime));
      }
      //此对象存在也不能也不能确认它内存泄漏了,要检测此对象的gc root
      return findLeakTrace(analysisStartNanoTime, snapshot, leakingRef);
    } catch (Throwable e) {
      return failure(e, since(analysisStartNanoTime));
    }
  }

我们重点看一下findLeakingReference方法

  private Instance findLeakingReference(String key, Snapshot snapshot) {
    //因为需要检测的类都构造了一个KeyedWeakReference,因此先找到KeyedWeakReference,就可以找到我们的对象
    ClassObj refClass = snapshot.findClass(KeyedWeakReference.class.getName());
    List<String> keysFound = new ArrayList<>();
    //循环所有KeyedWeakReference实例
    for (Instance instance : refClass.getInstancesList()) {
      List<ClassInstance.FieldValue> values = classInstanceValues(instance);
      //找到KeyedWeakReference里面的key值,此值在我们前面传入的对象唯一标示
      String keyCandidate = asString(fieldValue(values, "key"));
      //当key值相等时就表示是我们的检测对象
      if (keyCandidate.equals(key)) {
        return fieldValue(values, "referent");
      }
      keysFound.add(keyCandidate);
    }
    throw new IllegalStateException(
        "Could not find weak reference with key " + key + " in " + keysFound);
  }
最后一步,也是最核心的方法,确认是否内存泄漏,和我们手动分析hprof的方法几乎相同
  private AnalysisResult findLeakTrace(long analysisStartNanoTime, Snapshot snapshot,
      Instance leakingRef) {

    //这两行代码是判断内存泄露的关键,我们在上篇中分析hprof文件,判断内存泄漏
    //判断的依据是展开调用到gc root,所谓gc root,就是不能被gc回收的对象,
    //gc root有很多类型,我们只要关注两种类型1.此对象是静态 2.此对象被其他线程使用,并且其他线程正在运行,没有结束
    //pathFinder.findPath方法中也就是判断这两种情况
    ShortestPathFinder pathFinder = new ShortestPathFinder(excludedRefs);
    ShortestPathFinder.Result result = pathFinder.findPath(snapshot, leakingRef);
    // 找不到引起内存泄漏的gc root,就表示此对象未泄漏
    // False alarm, no strong reference path to GC Roots.
    if (result.leakingNode == null) {
      return noLeak(since(analysisStartNanoTime));
    }

    //生成泄漏的调用栈,为了在通知栏中显示
    LeakTrace leakTrace = buildLeakTrace(result.leakingNode);

    String className = leakingRef.getClassObj().getClassName();

    // Side effect: computes retained size.
    snapshot.computeDominators();

    Instance leakingInstance = result.leakingNode.instance;

    //计算泄漏的空间大小
    long retainedSize = leakingInstance.getTotalRetainedSize();

    retainedSize += computeIgnoredBitmapRetainedSize(snapshot, leakingInstance);

    return leakDetected(result.excludingKnownLeaks, className, leakTrace, retainedSize,
        since(analysisStartNanoTime));
  }

核心的代码我们已经看完了,是不是有一种豁然开朗的感觉,这就是好的软件,将重复繁琐的工作封装起来,只给我们留下一个两行的使用说明









作者:u011291205 发表于2016/9/10 23:51:08 原文链接
阅读:49 评论:0 查看评论

Android SwipeRefreshLayout下拉刷新控件源码简单分析

$
0
0

       咱们在做Android APP开发的时候经常碰到有下拉刷新和上拉加载跟多的需求,这篇文章咱们先说说下来刷新,咱们就以google的原生的下拉刷新控件SwipeRefreshLayout来看看大概的实现过程。

       SwipeRefreshLayout是google自己推出的下拉刷新控件。使用起来也非常的简单,在满足条件的情况下下拉的时候会显示一个圆形的loading的动画效果,然后回调到上层,上层自己做刷新的一系列的处理,处理结束后调用SwipeRefreshLayout的setRefreshing(false)告诉SwipeRefreshLayout完成刷新。具体的效果图如下
这里写图片描述

       那接下来我们就来简单的看下SwipeRefreshLayout内部是怎么实现的下拉刷新。准备从三个CircleImageView,MaterialProgressDrawable,SwipeRefreshLayout相关的类着手来分析下拉刷新代码简单实现。

一. CircleImageView类代码分析

       继承自ImageView,CircleImageView是一个圆形的并且底部是有一定阴影效果的ImageView。正如上图中下拉刷新的时候显示的那个白色的小圆。

       CircleImageView的具体实现。里面的代码非常的少就干了两件事一个是确定圆形,一个是圆形底部的阴影效果(包括向下兼容的情况)。具体的实现我就干脆写在代码的注释里面了,CircleImageView包所在的路径android.support.v4.widget。

       CircleImageView构造函数

    public CircleImageView(Context context, int color, final float radius) {
        super(context);
        final float density = getContext().getResources().getDisplayMetrics().density;
        final int diameter = (int) (radius * density * 2);
        final int shadowYOffset = (int) (density * Y_OFFSET);
        final int shadowXOffset = (int) (density * X_OFFSET);

        mShadowRadius = (int) (density * SHADOW_RADIUS);

        ShapeDrawable circle;
        if (elevationSupported()) {
            // 确保是一个圆形
            circle = new ShapeDrawable(new OvalShape());
            // 如果版本支持阴影的设置,直接调用setElevation函数设置阴影效果
            ViewCompat.setElevation(this, SHADOW_ELEVATION * density);
        } else {
            // 如果版本不支持阴影效果的设置,没办了只能自己去实现一个类似的效果了。
            // OvalShadow是继承自OvalShape自定义的一个类,用来实现类似的阴影效果(这个可能是我们的一个学习的点)。
            OvalShape oval = new OvalShadow(mShadowRadius, diameter);
            circle = new ShapeDrawable(oval);
            // 关闭硬件加速,要不绘制的阴影没有效果
            ViewCompat.setLayerType(this, ViewCompat.LAYER_TYPE_SOFTWARE, circle.getPaint());
            // 设置阴影层,Y方向稍微偏移了一点点
            circle.getPaint().setShadowLayer(mShadowRadius, shadowXOffset, shadowYOffset, KEY_SHADOW_COLOR);
            final int padding = mShadowRadius;
            // 保证接下的内容不会绘制到阴影上面去,但是阴影被覆盖住。
            setPadding(padding, padding, padding, padding);
        }
        circle.getPaint().setColor(color);
        setBackgroundDrawable(circle);
    }

       CircleImageView测量函数

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        if (!elevationSupported()) {
            // 如果不支持阴影效果,把阴影的范围加进去重新设置控件的大小
            setMeasuredDimension(getMeasuredWidth() + mShadowRadius * 2, getMeasuredHeight() + mShadowRadius * 2);
        }
    }

       为了向下兼容实现类似阴影效果而自定义的类

    /**
     * 继承自OvalShape,先保证图像是圆形的。重写draw方法实现一个类似阴影的效果
     */
    private class OvalShadow extends OvalShape {

        private RadialGradient mRadialGradient;
        private Paint          mShadowPaint;
        private int            mCircleDiameter;

        public OvalShadow(int shadowRadius, int circleDiameter) {
            super();
            // 画阴影的paint
            mShadowPaint = new Paint();
            // 阴影的范围大小
            mShadowRadius = shadowRadius;
            // 直径
            mCircleDiameter = circleDiameter;
            // 环形渲染,达到阴影的效果
            mRadialGradient = new RadialGradient(mCircleDiameter / 2, mCircleDiameter / 2, mShadowRadius, new int[]{FILL_SHADOW_COLOR,
                                                                                                                    Color.TRANSPARENT},
                                                 null, Shader.TileMode.CLAMP);
            mShadowPaint.setShader(mRadialGradient);
        }

        @Override
        public void draw(Canvas canvas, Paint paint) {
            final int viewWidth = CircleImageView.this.getWidth();
            final int viewHeight = CircleImageView.this.getHeight();
            // 先画上阴影效果
            canvas.drawCircle(viewWidth / 2, viewHeight / 2, (mCircleDiameter / 2 + mShadowRadius), mShadowPaint);
            // 画上内容
            canvas.drawCircle(viewWidth / 2, viewHeight / 2, (mCircleDiameter / 2), paint);
        }
    }

一. MaterialProgressDrawable类代码分析

       继承自Drawable,这个Drawable干的事情就是当下拉刷新进入加载的时候显示一个小圆环,并且这个小圆环是可以一直转圈的,正如上文效果图中一直转圈并且颜色不同变化的情况就是通过MaterialProgressDrawable来实现的。

       MaterialProgressDrawable继承自Drawable,既然是继承自Drawable那咱们首先关注重写的getIntrinsicHeight() getIntrinsicWidth() draw(Canvas c) setAlpha(int alpha)这些方法。其中getIntrinsicHeight和getIntrinsicWidth用来给依附的view提供测量大小,draw函数就是Drawable具体的内容了,setAlpha设置透明度。我们就直接看draw()函数了。

    @Override
    public void draw(Canvas c) {
        // 自定义Drawable的时候draw函数是关键部分
        final Rect bounds = getBounds(); // 获取Drawable的区域
        final int saveCount = c.save();
        // 旋转mRotation角度
        c.rotate(mRotation, bounds.exactCenterX(), bounds.exactCenterY());
        // 这个里面就开始画箭头和转圈的小圆环了
        mRing.draw(c, bounds);
        c.restoreToCount(saveCount);
    }

在draw函数中mRing.draw(c, bounds);就是来绘制转圈的那个圆环的。调用的是内部类Ring的draw()函数,进入看下咯。

        public void draw(Canvas c, Rect bounds) {
            final RectF arcBounds = mTempBounds;
            arcBounds.set(bounds);
            // 进度条相对于外圈的一个内边距
            arcBounds.inset(mStrokeInset, mStrokeInset);

            final float startAngle = (mStartTrim + mRotation) * 360;
            final float endAngle = (mEndTrim + mRotation) * 360;
            float sweepAngle = endAngle - startAngle;

            mPaint.setColor(mCurrentColor);
            // 画进度圆环(环的宽度setStrokeWidth)
            c.drawArc(arcBounds, startAngle, sweepAngle, false, mPaint);

            // 如果需要的话,画箭头
            drawTriangle(c, startAngle, sweepAngle, bounds);

            if (mAlpha < 255) {
                // 在上面覆盖一层alpha,达到透明的效果
                mCirclePaint.setColor(mBackgroundColor);
                mCirclePaint.setAlpha(255 - mAlpha);
                c.drawCircle(bounds.exactCenterX(), bounds.exactCenterY(), bounds.width() / 2, mCirclePaint);
            }
        }

        private void drawTriangle(Canvas c, float startAngle, float sweepAngle, Rect bounds) {
            if (mShowArrow) {
                // 如果现实箭头
                if (mArrow == null) {
                    mArrow = new android.graphics.Path();
                    mArrow.setFillType(android.graphics.Path.FillType.EVEN_ODD);
                } else {
                    mArrow.reset();
                }

                // 找到三角形箭头要偏移的位置(x,y方向要偏移的位置)
                float inset = (int) mStrokeInset / 2 * mArrowScale;
                float x = (float) (mRingCenterRadius * Math.cos(0) + bounds.exactCenterX());
                float y = (float) (mRingCenterRadius * Math.sin(0) + bounds.exactCenterY());

                // 先确定三角形箭头的三个点,在偏移到0度角的位置,然后再旋转进度条扫过的角度,在封闭形成三角形箭头
                mArrow.moveTo(0, 0);
                mArrow.lineTo(mArrowWidth * mArrowScale, 0);
                mArrow.lineTo((mArrowWidth * mArrowScale / 2), (mArrowHeight * mArrowScale));
                mArrow.offset(x - inset, y);
                mArrow.close();
                // draw a triangle
                mArrowPaint.setColor(mCurrentColor);
                c.rotate(startAngle + sweepAngle - ARROW_OFFSET_ANGLE, bounds.exactCenterX(), bounds.exactCenterY());
                c.drawPath(mArrow, mArrowPaint);
            }
        }

画圆环,画圆环上面的三角形箭头有了吧。到现在图形是有了,但是啥时候开始转圈啥时候停止转圈动画呢。看MaterialProgressDrawable的start()和stop()函数,对应的就是开始结束转圈的动画。看看start()里面到底做的是写啥。

    // MaterialProgressDrawable释放的时候开始转圈动画,没转一圈换一个颜色
    @Override
    public void start() {
        mAnimation.reset();
        // 进度圆环保存一些mStartTrim,mEndTrim,mRotation设置信息
        mRing.storeOriginals();
        if (mRing.getEndTrim() != mRing.getStartTrim()) {
            // 有进度圆环的时候,这个时候做的事情会先慢慢的把这个现有的圆环慢慢的变小,然后在开始转圈
            mFinishing = true;
            mAnimation.setDuration(ANIMATION_DURATION / 2);
            mParent.startAnimation(mAnimation);
        } else {
            // 没有进度圆环的时候,直接开始转圈的动画
            mRing.setColorIndex(0);
            mRing.resetOriginals();
            mAnimation.setDuration(ANIMATION_DURATION);
            mParent.startAnimation(mAnimation);
        }
    }

恩,都是在和mAnimation变量打交道。接着看下mAnimation干啥用的。

    private void setupAnimators() {
        final MaterialProgressDrawable.Ring ring = mRing;
        final Animation animation = new Animation() {
            @Override
            public void applyTransformation(float interpolatedTime, Transformation t) {
                if (mFinishing) {
                    // 在有进度圆环的时候我们去启动转圈的动画的时候是要先把这个圆环慢慢的变小消失
                    applyFinishTranslation(interpolatedTime, ring);
                } else {
                    final float minProgressArc = getMinProgressArc(ring);
                    final float startingEndTrim = ring.getStartingEndTrim();
                    final float startingTrim = ring.getStartingStartTrim();
                    final float startingRotation = ring.getStartingRotation();
                    // 每次repeat的动画在最后的25%的过程中颜色有过渡的效果
                    updateRingColor(interpolatedTime, ring);

                    // 每次repeat的动画的前50%的时候圆环的起始角度有一个往前移的动作
                    if (interpolatedTime <= START_TRIM_DURATION_OFFSET) {
                        final float scaledTime = (interpolatedTime) / (1.0f - START_TRIM_DURATION_OFFSET);
                        final float startTrim = startingTrim +
                                                ((MAX_PROGRESS_ARC - minProgressArc) * MATERIAL_INTERPOLATOR.getInterpolation(scaledTime));
                        ring.setStartTrim(startTrim);
                    }

                    // 每次repeat的动画的后50%的时候圆环的结束角度有一个往前移的动作
                    if (interpolatedTime > END_TRIM_START_DELAY_OFFSET) {
                        final float minArc = MAX_PROGRESS_ARC - minProgressArc;
                        float scaledTime = (interpolatedTime - START_TRIM_DURATION_OFFSET) / (1.0f - START_TRIM_DURATION_OFFSET);
                        final float endTrim = startingEndTrim + (minArc * MATERIAL_INTERPOLATOR.getInterpolation(scaledTime));
                        ring.setEndTrim(endTrim);
                    }

                    final float rotation = startingRotation + (0.25f * interpolatedTime);
                    // 圆环旋转的效果
                    ring.setRotation(rotation);

                    float groupRotation = ((FULL_ROTATION / NUM_POINTS) * interpolatedTime) +
                                          (FULL_ROTATION * (mRotationCount / NUM_POINTS));
                    setRotation(groupRotation);
                }
            }
        };
        animation.setRepeatCount(Animation.INFINITE);
        animation.setRepeatMode(Animation.RESTART);
        animation.setInterpolator(LINEAR_INTERPOLATOR);
        animation.setAnimationListener(new Animation.AnimationListener() {

            @Override
            public void onAnimationStart(Animation animation) {
                mRotationCount = 0;
            }

            @Override
            public void onAnimationEnd(Animation animation) {
                // do nothing
            }

            @Override
            public void onAnimationRepeat(Animation animation) {
                // 转一圈圆环换一个颜色
                ring.storeOriginals();
                ring.goToNextColor();
                ring.setStartTrim(ring.getEndTrim());
                if (mFinishing) {
                    // 在SwipeRefreshLayout中调用MaterialProgressDrawable类start函数的时候,
                    // 如果有圆环第一次动画就是圆环慢慢消失,这里表示消失完成了
                    mFinishing = false;
                    animation.setDuration(ANIMATION_DURATION);
                    ring.setShowArrow(false);
                } else {
                    mRotationCount = (mRotationCount + 1) % (NUM_POINTS);
                }
            }
        });
        mAnimation = animation;
    }

    // 在有进度圆环的时候我们去启动转圈的动画的时候是要先把这个圆环慢慢的变小消失
    private void applyFinishTranslation(float interpolatedTime, MaterialProgressDrawable.Ring ring) {
        // 进度圆环的颜色有一个过渡的效果
        updateRingColor(interpolatedTime, ring);
        // 一次动画要转的rotation
        float targetRotation = (float) (Math.floor(ring.getStartingRotation() / MAX_PROGRESS_ARC) + 1f);
        final float minProgressArc = getMinProgressArc(ring);
        final float startTrim = ring.getStartingStartTrim() +
                                (ring.getStartingEndTrim() - minProgressArc - ring.getStartingStartTrim()) * interpolatedTime;
        // 在一圈的过程中进度圆环是慢慢变小的所以setEndTrim是没变化的
        ring.setStartTrim(startTrim);
        ring.setEndTrim(ring.getStartingEndTrim());
        final float rotation = ring.getStartingRotation() + ((targetRotation - ring.getStartingRotation()) * interpolatedTime);
        // 在一圈的过程中进度圆环会慢慢往前旋转的
        ring.setRotation(rotation);
    }

看的出来mAnimation是自定义的一个Animation(自定义Animation的时候重心在applyTransformation函数上面会随着动画的进行不断的回调这个函数)。如果在我们调用MaterialProgressDrawable start()函数的时候如果有小圆圈的显示动画的第一次repeat的时候会把这个小圆圈慢慢的变小从applyFinishTranslation()可以分析得到。然后才开始一圈一圈的转圈并且每次repeat的时候会换一种颜色。

三. SwipeRefreshLayout类代码分析

       本文最重要的一个类来了,这个才是下拉刷新接触最多的一个类,下拉刷新打不的逻辑都集中在这个类当中。SwipeRefreshLayout继承自ViewGroup是一个容器控件。既然是一个自定义的容器类那咱们就从onMeasure(),onLayout(),onInterceptTouchEvent(),onTouchEvent()四个函数入手来分析SwipeRefreshLayout的过程。

1). SwipeRefreshLayout类onMeasure()函数

       从onMeasure()函数我们可以得到SwipeRefreshLayout中控件的测量规则,看看onMeasure()的具体实现

    private void ensureTarget() {
        // 取了第一个不是mCircleView的view作为mTarget View
        if (mTarget == null) {
            for (int i = 0; i < getChildCount(); i++) {
                View child = getChildAt(i);
                if (!child.equals(mCircleView)) {
                    mTarget = child;
                    break;
                }
            }
        }
    }

    @Override
    public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        if (mTarget == null) {
            ensureTarget();
        }
        if (mTarget == null) {
            return;
        }
        // mTarget这个就是咱们的内容控件,直接适用了SwipeRefreshLayout的整个大小
        mTarget.measure(MeasureSpec.makeMeasureSpec(getMeasuredWidth() - getPaddingLeft() - getPaddingRight(), MeasureSpec.EXACTLY),
                        MeasureSpec.makeMeasureSpec(getMeasuredHeight() - getPaddingTop() - getPaddingBottom(), MeasureSpec.EXACTLY));
        // mCircleView这个就是咱们下拉和加载的时候显示的那个小圆圈在构造函数中addView,给了确定的大小,具体可以参SwipeRefreshLayout的构造函数
        mCircleView.measure(MeasureSpec.makeMeasureSpec(mCircleWidth, MeasureSpec.EXACTLY),
                            MeasureSpec.makeMeasureSpec(mCircleHeight, MeasureSpec.EXACTLY));
        // 确定mCircleView初始的偏移位置和当前位置
        if (!mUsingCustomStart && !mOriginalOffsetCalculated) {
            mOriginalOffsetCalculated = true;
            mCurrentTargetOffsetTop = mOriginalOffsetTop = -mCircleView.getMeasuredHeight();
        }
        // mCircleView在SwipeRefreshLayout中的子View的index
        mCircleViewIndex = -1;
        // Get the index of the circleview.
        for (int index = 0; index < getChildCount(); index++) {
            if (getChildAt(index) == mCircleView) {
                mCircleViewIndex = index;
                break;
            }
        }
    }

从上面代码分析咱可以看得出来SwipeRefreshLayout只关心两个View:mTarget、mCircleView。其中mTarget是内容控件,mCircleView下拉或者刷新过程中显示的小圆控件。同时mTarget的大小设置了整个SwipeRefreshLayout的大小所以咱们在xml中设置的大小应该是不算数的。

2). SwipeRefreshLayout类onLayout()函数

       从onLayout()函数我们可以得到SwipeRefreshLayout中控件的布局规则

    @Override
    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
        final int width = getMeasuredWidth();
        final int height = getMeasuredHeight();
        if (getChildCount() == 0) {
            return;
        }
        if (mTarget == null) {
            ensureTarget();
        }
        if (mTarget == null) {
            return;
        }
        final View child = mTarget;
        final int childLeft = getPaddingLeft();
        final int childTop = getPaddingTop();
        final int childWidth = width - getPaddingLeft() - getPaddingRight();
        final int childHeight = height - getPaddingTop() - getPaddingBottom();
        // 设置mTarget的位置,正常布局没啥看头
        child.layout(childLeft, childTop, childLeft + childWidth, childTop + childHeight);
        int circleWidth = mCircleView.getMeasuredWidth();
        int circleHeight = mCircleView.getMeasuredHeight();
        // 设置mCircleView,也是正常布局就偏移了mCurrentTargetOffsetTop的高度,这个好理解咱mCircleView是会上下滑动的
        mCircleView.layout((width / 2 - circleWidth / 2), mCurrentTargetOffsetTop, (width / 2 + circleWidth / 2),
                           mCurrentTargetOffsetTop + circleHeight);
    }

onLayout()还是中规中矩的,分别布局了mTarget和mCircleView

3). SwipeRefreshLayout类onInterceptTouchEvent()函数

       onInterceptTouchEvent()用来对触摸事件做拦截处理。如果拦截了就不会想子View传递了。关于事件的拦截想多说已经如果ACTION_DOWN被拦截下来了那么该事件接下来的ACTION_MOV和EACTION_UP也不会往下传递。

    /**
     * 就是去判断mTarget是否有向上滑动,有一个向上的scroll。如果有这个时候肯定是不能下拉刷新的吧
     */
    public boolean canChildScrollUp() {
        if (android.os.Build.VERSION.SDK_INT < 14) {
            if (mTarget instanceof AbsListView) {
                final AbsListView absListView = (AbsListView) mTarget;
                return absListView.getChildCount() > 0 &&
                       (absListView.getFirstVisiblePosition() > 0 || absListView.getChildAt(0).getTop() < absListView.getPaddingTop());
            } else {
                return ViewCompat.canScrollVertically(mTarget, -1) || mTarget.getScrollY() > 0;
            }
        } else {
            return ViewCompat.canScrollVertically(mTarget, -1);
        }
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent ev) {
        ensureTarget();

        final int action = MotionEventCompat.getActionMasked(ev);

        // mReturningToStart好像没啥作用,一直是false
        if (mReturningToStart && action == MotionEvent.ACTION_DOWN) {
            mReturningToStart = false;
        }

        // 如果mTarget这个时候有向上滑动有scroll y(这个时候是不满足下拉刷新的条件的),或者正在刷新。事件不拦截个字View去处理。
        // 从这里也可以看出当正在刷新的时候子View还是会想要按键事件的。
        if (!isEnabled() || mReturningToStart || canChildScrollUp() || mRefreshing) {
            // 不拦截
            return false;
        }

        switch (action) {
            case MotionEvent.ACTION_DOWN://ACTION_DOWN这个时间是不拦截的
                // mCircleView移动到起始位置。(mOriginalOffsetTop设置的初始位置+mCircleView设置的top位置)
                setTargetOffsetTopAndBottom(mOriginalOffsetTop - mCircleView.getTop(), true);
                mActivePointerId = MotionEventCompat.getPointerId(ev, 0);
                // 标记下拉是否开始了
                mIsBeingDragged = false;
                final float initialDownY = getMotionEventY(ev, mActivePointerId);
                if (initialDownY == -1) {
                    return false;
                }
                mInitialDownY = initialDownY;
                break;

            case MotionEvent.ACTION_MOVE:
                if (mActivePointerId == INVALID_POINTER) {
                    Log.e(LOG_TAG, "Got ACTION_MOVE event but don't have an active pointer id.");
                    return false;
                }

                final float y = getMotionEventY(ev, mActivePointerId);
                if (y == -1) {
                    return false;
                }
                final float yDiff = y - mInitialDownY;
                // y方向有滑动
                if (yDiff > mTouchSlop && !mIsBeingDragged) {
                    mInitialMotionY = mInitialDownY + mTouchSlop;
                    // 下拉开始,从这个时候开始当前事件一直到ACTION_UP之间的事件我们是会拦截下来的
                    mIsBeingDragged = true;
                    mProgress.setAlpha(STARTING_PROGRESS_ALPHA);
                }
                break;

            case MotionEventCompat.ACTION_POINTER_UP:
                onSecondaryPointerUp(ev);
                break;

            case MotionEvent.ACTION_UP:
            case MotionEvent.ACTION_CANCEL:
                mIsBeingDragged = false;
                mActivePointerId = INVALID_POINTER;
                break;
        }
        return mIsBeingDragged;
    }

先判断是否满足下拉刷新的条件,同时咱也看的出来ACTION_DOWN不去做拦截处理。主要的拦截在ACTION_MOVE里面。当满足下拉刷新的条件并且下拉了那不好意思这次的时间我SwipeRefreshLayout要强行插手处理了。接下来就得去onTouchEvent()函数了。

4). SwipeRefreshLayout类onTouchEvent()函数

       onTouchEvent()SwipeRefreshLayout对具体的事件都在这个函数里面了。

    @Override
    public boolean onTouchEvent(MotionEvent ev) {
        final int action = MotionEventCompat.getActionMasked(ev);

        if (mReturningToStart && action == MotionEvent.ACTION_DOWN) {
            mReturningToStart = false;
        }
        // 如果mTarget这个时候有向上滑动有scroll, SwipeRefreshLayout不对该事件做处理
        if (!isEnabled() || mReturningToStart || canChildScrollUp()) {
            return false;
        }

        switch (action) {
            case MotionEvent.ACTION_DOWN:
                mActivePointerId = MotionEventCompat.getPointerId(ev, 0);
                mIsBeingDragged = false;
                break;

            case MotionEvent.ACTION_MOVE: {
                final int pointerIndex = MotionEventCompat.findPointerIndex(ev, mActivePointerId);
                if (pointerIndex < 0) {
                    Log.e(LOG_TAG, "Got ACTION_MOVE event but have an invalid active pointer id.");
                    return false;
                }

                final float y = MotionEventCompat.getY(ev, pointerIndex);
                final float overscrollTop = (y - mInitialMotionY) * DRAG_RATE;
                if (mIsBeingDragged) {
                    if (overscrollTop > 0) {
                        // 可以处理下拉了,mCircleView会随着手指往下移动了
                        moveSpinner(overscrollTop);
                    } else {
                        return false;
                    }
                }
                break;
            }
            case MotionEventCompat.ACTION_POINTER_DOWN: {
                final int index = MotionEventCompat.getActionIndex(ev);
                mActivePointerId = MotionEventCompat.getPointerId(ev, index);
                break;
            }

            case MotionEventCompat.ACTION_POINTER_UP:
                onSecondaryPointerUp(ev);
                break;

            case MotionEvent.ACTION_UP:
            case MotionEvent.ACTION_CANCEL: {
                if (mActivePointerId == INVALID_POINTER) {
                    if (action == MotionEvent.ACTION_UP) {
                        Log.e(LOG_TAG, "Got ACTION_UP event but don't have an active pointer id.");
                    }
                    return false;
                }
                final int pointerIndex = MotionEventCompat.findPointerIndex(ev, mActivePointerId);
                final float y = MotionEventCompat.getY(ev, pointerIndex);
                final float overscrollTop = (y - mInitialMotionY) * DRAG_RATE;
                mIsBeingDragged = false;
                // 是否触摸的时候,mCircleView会到指定的位置,必要的话进入刷新的状态
                finishSpinner(overscrollTop);
                mActivePointerId = INVALID_POINTER;
                return false;
            }
        }

        return true;
    }

重心在MotionEvent.ACTION_MOVE和MotionEvent.ACTION_UP上面正好对应了moveSpinner()和finishSpinner()函数。咱们先分析moveSpinner()这个函数做的事情就是随着手指的下拉mCircleView做相应的位移操作并且mCircleView里面的mProgress(MaterialProgressDrawable)做相应的动态变化。

    /**
     * 下拉过程中调用该函数
     * @param overscrollTop:表示y轴上下拉的距离
     */
    private void moveSpinner(float overscrollTop) {
        mProgress.showArrow(true);
        // 相对于刷新距离滑动了百分之多少(注意如果超过了刷新的距离这个值会大于1的)
        float originalDragPercent = overscrollTop / mTotalDragDistance;
        // 控制最大值为1 dragPercent == 1 表示滑动距离已经到了刷新的条件了
        float dragPercent = Math.min(1f, Math.abs(originalDragPercent));
        // 调整下百分比(小于0.4的情况下设置为0)
        float adjustedPercent = (float) Math.max(dragPercent - .4, 0) * 5 / 3;
        // 相对于进入刷新的位置的偏移量,注意这个值可能是负数。负数表示还没有达到刷新的距离
        float extraOS = Math.abs(overscrollTop) - mTotalDragDistance;
        // 这里去计算小圆圈在Y轴上面可以滑动到的距离(targetY)为啥要这样算就没搞明白
        float slingshotDist = mUsingCustomStart ? mSpinnerFinalOffset - mOriginalOffsetTop : mSpinnerFinalOffset;
        float tensionSlingshotPercent = Math.max(0, Math.min(extraOS, slingshotDist * 2) / slingshotDist);
        float tensionPercent = (float) ((tensionSlingshotPercent / 4) - Math.pow((tensionSlingshotPercent / 4), 2)) * 2f;
        float extraMove = (slingshotDist) * tensionPercent * 2;
        int targetY = mOriginalOffsetTop + (int) ((slingshotDist * dragPercent) + extraMove);
        // 在手指滑动的过程中mCircleView小圆圈是可见的
        if (mCircleView.getVisibility() != View.VISIBLE) {
            mCircleView.setVisibility(View.VISIBLE);
        }
        if (!mScale) {
            // 在滑动过程中小圆圈设置不缩放,x,y scale都设置为1
            ViewCompat.setScaleX(mCircleView, 1f);
            ViewCompat.setScaleY(mCircleView, 1f);
        }
        if (overscrollTop < mTotalDragDistance) {
            // 还没达到刷新的距离的时候
            if (mScale) {
                // 如果设置了小圆圈在滑动的过程中可以缩放,scale慢慢的变大
                setAnimationProgress(overscrollTop / mTotalDragDistance);
            }
            if (mProgress.getAlpha() > STARTING_PROGRESS_ALPHA && !isAnimationRunning(mAlphaStartAnimation)) {
                // 其实这里也可以看出来,在没有达到刷新距离的时候,alpha会尽量保持是STARTING_PROGRESS_ALPHA的(相对来说模糊点)
                startProgressAlphaStartAnimation();
            }
            float strokeStart = adjustedPercent * .8f;
            // 设置小圆圈里面进度条的开始和结束位置(在还没有达到刷新距离的时候小圆圈里面进度条是慢慢变大的,最多达到80%的圈)
            mProgress.setStartEndTrim(0f, Math.min(MAX_PROGRESS_ANGLE, strokeStart));
            // 设置mCircleView小圆圈里面进度条箭头的缩放大小(在还没有达到刷新距离的时候小圆圈进度条箭头是慢慢变大的)
            mProgress.setArrowScale(Math.min(1f, adjustedPercent));
        } else {
            // 达到了刷新的距离的时候(注意这个时候小圆圈里面进度条占80%,并且是可见的)
            if (mProgress.getAlpha() < MAX_ALPHA && !isAnimationRunning(mAlphaMaxAnimation)) {
                // 其实这里也可以看出来,在达到刷新距离的时候,alpha会尽量保持是MAX_ALPHA的(完全显示)
                startProgressAlphaMaxAnimation();
            }
        }
        float rotation = (-0.25f + .4f * adjustedPercent + tensionPercent * 2) * .5f;
        // 设置小圆圈进度条的旋转角度,在下拉的过程中mCircleView小圆圈是一点一点往前旋转的
        mProgress.setProgressRotation(rotation);
        // mCircleView会随着手指往下移动
        setTargetOffsetTopAndBottom(targetY - mCurrentTargetOffsetTop, true /* requires update */);
    }

    /**
     * mCircleView做缩放操作
     */
    private void setAnimationProgress(float progress) {
        if (isAlphaUsedForScale()) {
            setColorViewAlpha((int) (progress * MAX_ALPHA));
        } else {
            ViewCompat.setScaleX(mCircleView, progress);
            ViewCompat.setScaleY(mCircleView, progress);
        }
    }

    // 启动一个alpha变化的动画,从当前值到STARTING_PROGRESS_ALPHA的变化
    private void startProgressAlphaStartAnimation() {
        mAlphaStartAnimation = startAlphaAnimation(mProgress.getAlpha(), STARTING_PROGRESS_ALPHA);
    }

当然里面涉及到的东西比较都,直接一笔带过了哦。
接下来咱来看看都手指松开的时候调用的finishSpinner()函数。

    /**
     * 下拉结束的时候调用该函数
     * @param overscrollTop: 表示y轴上下拉的距离
     */
    private void finishSpinner(float overscrollTop) {
        if (overscrollTop > mTotalDragDistance) {
            // 下拉结束的时候达到了刷新的距离,这个时候就要告诉上层该进入刷新了
            setRefreshing(true, true /* notify */);
        } else {
            // 下拉结束的时候还没有达到刷新的距离
            mRefreshing = false;
            // 小圆圈进度条消失
            mProgress.setStartEndTrim(0f, 0f);
            Animation.AnimationListener listener = null;
            if (!mScale) {
                // 小圆圈没有设置缩放
                listener = new Animation.AnimationListener() {

                    @Override
                    public void onAnimationStart(Animation animation) {
                    }

                    @Override
                    public void onAnimationEnd(Animation animation) {
                        if (!mScale) {
                            // 如果小圆圈没有设置缩放,当会到了初始位置之后scale缩小为0,不可见
                            startScaleDownAnimation(null);
                        }
                    }

                    @Override
                    public void onAnimationRepeat(Animation animation) {
                    }

                };
            }
            // 小圆圈从当前位置返回到初始位置
            animateOffsetToStartPosition(mCurrentTargetOffsetTop, listener);
            // 小圆圈里面进度条不显示箭头了
            mProgress.showArrow(false);
        }
    }

准备进入刷新状态的时候调用的是setRefreshing()函数。

    /**
     * 是指是否进入刷新状态
     * @param refreshing: 是否进入刷新状态
     * @param notify:是否通知上层,SwipeRefreshLayout的时候定义OnRefreshListener的监听
     */
    private void setRefreshing(boolean refreshing, final boolean notify) {
        if (mRefreshing != refreshing) {
            // 当前状态不相同
            mNotify = notify;
            ensureTarget();
            mRefreshing = refreshing;
            if (mRefreshing) {
                // 进入刷新状态,
                animateOffsetToCorrectPosition(mCurrentTargetOffsetTop, mRefreshListener);
            } else {
                // 进入非刷新状态,直接scale缩小为0了
                startScaleDownAnimation(mRefreshListener);
            }
        }
    }

咱还是看进入刷新状态的情况,调用的是animateOffsetToCorrectPosition()函数。两个参数一个是mCurrentTargetOffsetTop:mCircleView的当前top位置,一个是mRefreshListener:动画开始,结束,重复的监听。animateOffsetToCorrectPosition()函数的启动一个动画引导mCircleView到指定的位置,并且在动画结束的时候会进入到刷新的状态OnRefreshListener。动画的具体实现也比较的简单咱就不具体的贴出来了。

ps:分析的比较简单,希望对大家能有一点帮助。

作者:wuyuxing24 发表于2016/9/11 1:28:09 原文链接
阅读:26 评论:0 查看评论

Android View的事件分发机制(二)

$
0
0

如果你还没看我的第一篇事件分发机制的话,现在赶紧去看Android View的事件分发机制(一)
这一节才是真正的从源码的角度去分析View的事件分发机制,结合第一篇去看,理解会更深刻。首先,要明白我们分析的对象就是MotionEvent,它包括三种典型的事件类型:

  • ACTION_DOWN:手指刚接触屏幕。
  • ACTION_MOVE:手指在屏幕上移动。
  • ACTION_UP:手指从屏幕上松开的一瞬间。

下面内容摘自《Android 开发艺术探索》140页的3.4 View的事件分发机制 内容,所谓点击事件的事件分发,就是对MotionEvent事件的分发过程,当MotionEvent事件产生之后,系统需要把这个事件传递给一个具体的View,其实这个传递的过程就是事件的一个分发过程。点击事件的分发过程由三个很重要的方法来共同完成:dispatchTouchEvent、onInterceptTouchEvent和onTouchEvent。

  1. dispatchTouchEvent(MotionEvent ev):用来进行事件的分发。如果事件能够传递给当前的View,那么此方法一定会被调用,返回结果受当前View的OnTouchEvent和下级View的dispatchTouchEvent方法的影响,表示是否消耗(处理)当前事件
  2. onInterceptTouchEvent(MotionEvent ev):在上述方法内部调用,用来判断是否拦截某个事件,如果当前View拦截了某个事件,那么在同一个事件序列当中,此方法不会再次调用,返回结果表示是否拦截当前事件
  3. onTouchEvent(MotionEvent ev):在dispatchTouchEvent方法中调用,用来处理点击事件,返回结果表示是否消耗当前事件,如果不消耗,则在同一个事件序列中,当前View无法再次收到事件。

    上述三个方法的关系可以用下面的伪代码进行表示:

public boolean dispatchTouchEvent(MotionEvent event){
        boolean consume = false;
        if(onInterceptTouchEvent(event)){
            consume = onTouchEvent(event);
        }else{
            consume = child.dispatchTouchEvent(event);
        return consume;
    }

上面的伪代码将三者的关系表现的淋漓极致,一个点击事件的传递规则大致如下:
1. 对于一个点击事件的根ViewGroup来说,点击事件产生后,首先会传给它,这时它的dispatchTouchEvent就会被调用。
2. 如果这个ViewGroup的onInterceptTouchEvent方法返回true就表示要拦截当前事件,接着事件就会交给ViewGroup处理,即它的onTouchEvent方法就会被调用。
3. 如果这个ViewGroup的onInterceptTouchEvent方法返回false就表示它不拦截当前事件,这时当前事件就会继续传递给它的子元素,接着子元素的dispatchTouchEvent就会被调用,如此反复直到事件被最终处理。

当一个点击事件产生后,它的实际传递过程遵循如下顺序:
Activity- ->Window- ->View,事件总是最先传递给Activity,Activity再传递给Window,最后Window再传递给顶级View。

事件分发的源码解析:

点击事件用MotionEvent表示,当一个点击操作发生时,事件最先传递给当前的Activity,由Activity的dispatchTouchEvent来进行事件派发,具体的工作是由Activity的内部Window来完成的,那我们先从Activity的dispatchTouchEvent来开始分析

 public boolean dispatchTouchEvent(MotionEvent ev) {
        if (ev.getAction() == MotionEvent.ACTION_DOWN) {
            onUserInteraction();
        }
        if (getWindow().superDispatchTouchEvent(ev)) {
            return true;
        }
        return onTouchEvent(ev);
    }

进去瞧瞧onUserInteraction()方法,原来是一个空方法

/**
     * Called whenever a key, touch, or trackball event is dispatched to the activity.Implement this method if you wish to know that the user has
     * interacted with the device in some way while your activity is running. 
     * ……
     * /
public void onUserInteraction() {}

让我们再瞧瞧superDispatchTouchEvent()方法。

     * Used by custom windows, such as Dialog, to pass the touch screen event
     * further down the view hierarchy. Application developers should not need to implement or call this.
     */
    public abstract boolean superDispatchTouchEvent(MotionEvent event);

Android View的事件分发机制(一)中我们知道PhoneWindow是Window的唯一实现类,猜测PhoneWindow也会将事件直接传递给DecorView去实现。看看PhoneWindow中是如何实现这个方法的:

    @Override
    public boolean superDispatchTouchEvent(MotionEvent event) {
        return mDecor.superDispatchTouchEvent(event);
    }

果然不出我们所料,会在DecorView中去调用superDispatchTouchEvent这个方法,DecorView又将这个方法的实现交由他的父类ViewGroup去处理,ViewGroup中dispatchTouchEvent()实现的方法如下:

    @Override
    public boolean dispatchTouchEvent(MotionEvent ev) {
        if (mInputEventConsistencyVerifier != null) {
            mInputEventConsistencyVerifier.onTouchEvent(ev, 1);
        }

        // If the event targets the accessibility focused view and this is it, start
        // normal event dispatch. Maybe a descendant is what will handle the click.
        if (ev.isTargetAccessibilityFocus() && isAccessibilityFocusedViewOrHost()) {
            ev.setTargetAccessibilityFocus(false);
        }

        boolean handled = false;
        if (onFilterTouchEventForSecurity(ev)) {
            final int action = ev.getAction();
            final int actionMasked = action & MotionEvent.ACTION_MASK;

            // Handle an initial down.
            if (actionMasked == MotionEvent.ACTION_DOWN) {
                // Throw away all previous state when starting a new touch gesture.
                // The framework may have dropped the up or cancel event for the previous gesture
                // due to an app switch, ANR, or some other state change.
                cancelAndClearTouchTargets(ev);
                resetTouchState();
            }

            // Check for interception.
            final boolean intercepted;
            if (actionMasked == MotionEvent.ACTION_DOWN
                    || mFirstTouchTarget != null) {
                final boolean disallowIntercept = (mGroupFlags & FLAG_DISALLOW_INTERCEPT) != 0;
                if (!disallowIntercept) {
                    intercepted = onInterceptTouchEvent(ev);
                    ev.setAction(action); // restore action in case it was changed
                } else {
                    intercepted = false;
                }
            } else {
                // There are no touch targets and this action is not an initial down
                // so this view group continues to intercept touches.
                intercepted = true;
            }

            // If intercepted, start normal event dispatch. Also if there is already
            // a view that is handling the gesture, do normal event dispatch.
            if (intercepted || mFirstTouchTarget != null) {
                ev.setTargetAccessibilityFocus(false);
            }

            // Check for cancelation.
            final boolean canceled = resetCancelNextUpFlag(this)
                    || actionMasked == MotionEvent.ACTION_CANCEL;

            // Update list of touch targets for pointer down, if needed.
            final boolean split = (mGroupFlags & FLAG_SPLIT_MOTION_EVENTS) != 0;
            TouchTarget newTouchTarget = null;
            boolean alreadyDispatchedToNewTouchTarget = false;
            if (!canceled && !intercepted) {

                // If the event is targeting accessiiblity focus we give it to the
                // view that has accessibility focus and if it does not handle it
                // we clear the flag and dispatch the event to all children as usual.
                // We are looking up the accessibility focused host to avoid keeping
                // state since these events are very rare.
                View childWithAccessibilityFocus = ev.isTargetAccessibilityFocus()
                        ? findChildWithAccessibilityFocus() : null;

                if (actionMasked == MotionEvent.ACTION_DOWN
                        || (split && actionMasked == MotionEvent.ACTION_POINTER_DOWN)
                        || actionMasked == MotionEvent.ACTION_HOVER_MOVE) {
                    final int actionIndex = ev.getActionIndex(); // always 0 for down
                    final int idBitsToAssign = split ? 1 << ev.getPointerId(actionIndex)
                            : TouchTarget.ALL_POINTER_IDS;

                    // Clean up earlier touch targets for this pointer id in case they
                    // have become out of sync.
                    removePointersFromTouchTargets(idBitsToAssign);

                    final int childrenCount = mChildrenCount;
                    if (newTouchTarget == null && childrenCount != 0) {
                        final float x = ev.getX(actionIndex);
                        final float y = ev.getY(actionIndex);
                        // Find a child that can receive the event.
                        // Scan children from front to back.
                        final ArrayList<View> preorderedList = buildOrderedChildList();
                        final boolean customOrder = preorderedList == null
                                && isChildrenDrawingOrderEnabled();
                        final View[] children = mChildren;
                        for (int i = childrenCount - 1; i >= 0; i--) {
                            final int childIndex = customOrder
                                    ? getChildDrawingOrder(childrenCount, i) : i;
                            final View child = (preorderedList == null)
                                    ? children[childIndex] : preorderedList.get(childIndex);

                            // If there is a view that has accessibility focus we want it
                            // to get the event first and if not handled we will perform a
                            // normal dispatch. We may do a double iteration but this is
                            // safer given the timeframe.
                            if (childWithAccessibilityFocus != null) {
                                if (childWithAccessibilityFocus != child) {
                                    continue;
                                }
                                childWithAccessibilityFocus = null;
                                i = childrenCount - 1;
                            }

                            if (!canViewReceivePointerEvents(child)
                                    || !isTransformedTouchPointInView(x, y, child, null)) {
                                ev.setTargetAccessibilityFocus(false);
                                continue;
                            }

                            newTouchTarget = getTouchTarget(child);
                            if (newTouchTarget != null) {
                                // Child is already receiving touch within its bounds.
                                // Give it the new pointer in addition to the ones it is handling.
                                newTouchTarget.pointerIdBits |= idBitsToAssign;
                                break;
                            }

                            resetCancelNextUpFlag(child);
                            if (dispatchTransformedTouchEvent(ev, false, child, idBitsToAssign)) {
                                // Child wants to receive touch within its bounds.
                                mLastTouchDownTime = ev.getDownTime();
                                if (preorderedList != null) {
                                    // childIndex points into presorted list, find original index
                                    for (int j = 0; j < childrenCount; j++) {
                                        if (children[childIndex] == mChildren[j]) {
                                            mLastTouchDownIndex = j;
                                            break;
                                        }
                                    }
                                } else {
                                    mLastTouchDownIndex = childIndex;
                                }
                                mLastTouchDownX = ev.getX();
                                mLastTouchDownY = ev.getY();
                                newTouchTarget = addTouchTarget(child, idBitsToAssign);
                                alreadyDispatchedToNewTouchTarget = true;
                                break;
                            }

                            // The accessibility focus didn't handle the event, so clear
                            // the flag and do a normal dispatch to all children.
                            ev.setTargetAccessibilityFocus(false);
                        }
                        if (preorderedList != null) preorderedList.clear();
                    }

                    if (newTouchTarget == null && mFirstTouchTarget != null) {
                        // Did not find a child to receive the event.
                        // Assign the pointer to the least recently added target.
                        newTouchTarget = mFirstTouchTarget;
                        while (newTouchTarget.next != null) {
                            newTouchTarget = newTouchTarget.next;
                        }
                        newTouchTarget.pointerIdBits |= idBitsToAssign;
                    }
                }
            }

            // Dispatch to touch targets.
            if (mFirstTouchTarget == null) {
                // No touch targets so treat this as an ordinary view.
                handled = dispatchTransformedTouchEvent(ev, canceled, null,
                        TouchTarget.ALL_POINTER_IDS);
            } else {
                // Dispatch to touch targets, excluding the new touch target if we already
                // dispatched to it.  Cancel touch targets if necessary.
                TouchTarget predecessor = null;
                TouchTarget target = mFirstTouchTarget;
                while (target != null) {
                    final TouchTarget next = target.next;
                    if (alreadyDispatchedToNewTouchTarget && target == newTouchTarget) {
                        handled = true;
                    } else {
                        final boolean cancelChild = resetCancelNextUpFlag(target.child)
                                || intercepted;
                        if (dispatchTransformedTouchEvent(ev, cancelChild,
                                target.child, target.pointerIdBits)) {
                            handled = true;
                        }
                        if (cancelChild) {
                            if (predecessor == null) {
                                mFirstTouchTarget = next;
                            } else {
                                predecessor.next = next;
                            }
                            target.recycle();
                            target = next;
                            continue;
                        }
                    }
                    predecessor = target;
                    target = next;
                }
            }

            // Update list of touch targets for pointer up or cancel, if needed.
            if (canceled
                    || actionMasked == MotionEvent.ACTION_UP
                    || actionMasked == MotionEvent.ACTION_HOVER_MOVE) {
                resetTouchState();
            } else if (split && actionMasked == MotionEvent.ACTION_POINTER_UP) {
                final int actionIndex = ev.getActionIndex();
                final int idBitsToRemove = 1 << ev.getPointerId(actionIndex);
                removePointersFromTouchTargets(idBitsToRemove);
            }
        }

        if (!handled && mInputEventConsistencyVerifier != null) {
            mInputEventConsistencyVerifier.onUnhandledEvent(ev, 1);
        }
        return handled;
    }

这个方法比较长,这里还是做分段说明,先看下面一段,很显然,他描述的是当前View是否拦截点击事件的处理过程:

// Check for interception.
final boolean intercepted;
if (actionMasked == MotionEvent.ACTION_DOWN || mFirstTouchTarget != null) {
         final boolean disallowIntercept = (mGroupFlags & FLAG_DISALLOW_INTERCEPT) != 0;
        if (!disallowIntercept) {
            intercepted = onInterceptTouchEvent(ev);
            // restore action in case it was changed
            ev.setAction(action); 
                } else {
                    intercepted = false;
                }
            } else {
                // There are no touch targets and this action is not an initial down
            // so this view group continues to intercept touches.
                intercepted = true;
            }

从上述代码我们可以看出,ViewGroup在如下两种情况下回判断是否要拦截当前事件:事件类型为ACTION_DOWN或者mFirstTouchTarget != null。ACTION_DOWN事件好理解,那么mFirstTouchTarget != null是什么东东呢?这个从后面的代码逻辑可以看出来:
1. 当事件由ViewGroup的子元素成功处理是,mFirstTouchTarget 会被赋值并指向子元素。换句话说:当ViewGroup不拦截事件并将事件交由子元素处理时mFirstTouchTarget != null,发过来,一旦事件有当前ViewGroup拦截时mFirstTouchTarget != null就不成立。当ACTION_MOVE和ACTION_UP事件到来时,由于(actionMasked == MotionEvent.ACTION_DOWN || mFirstTouchTarget != null)这个条件为false,将会导致ViewGroup的onInterceptTouchEvent()不会再被调用,并且同一序列中的其他事件都会默认交给它处理。
2. 当然,这里有一种特殊情况,那就是FLAG_DISALLOW_INTERCEPT标记位,它的作用就是让ViewGroup不再拦截事件,当前前提是ViewGroup不拦截ACTION_DOWN 事件。

接着再看当ViewGroup不拦截事件的时候,事件会向下分发交由它的子View进行处理,这段源码如下:

final View[] children = mChildren;
                        for (int i = childrenCount - 1; i >= 0; i--) {
                            final int childIndex = customOrder
                                    ? getChildDrawingOrder(childrenCount, i) : i;
                            final View child = (preorderedList == null)
                                    ? children[childIndex] : preorderedList.get(childIndex);

                            // If there is a view that has accessibility focus we want it
                            // to get the event first and if not handled we will perform a
                            // normal dispatch. We may do a double iteration but this is
                            // safer given the timeframe.
                            if (childWithAccessibilityFocus != null) {
                                if (childWithAccessibilityFocus != child) {
                                    continue;
                                }
                                childWithAccessibilityFocus = null;
                                i = childrenCount - 1;
                            }

                            if (!canViewReceivePointerEvents(child)
                                    || !isTransformedTouchPointInView(x, y, child, null)) {
                                ev.setTargetAccessibilityFocus(false);
                                continue;
                            }

                            newTouchTarget = getTouchTarget(child);
                            if (newTouchTarget != null) {
                                // Child is already receiving touch within its bounds.
                                // Give it the new pointer in addition to the ones it is handling.
                                newTouchTarget.pointerIdBits |= idBitsToAssign;
                                break;
                            }

                            resetCancelNextUpFlag(child);
                            if (dispatchTransformedTouchEvent(ev, false, child, idBitsToAssign)) {
                                // Child wants to receive touch within its bounds.
                                mLastTouchDownTime = ev.getDownTime();
                                if (preorderedList != null) {
                                    // childIndex points into presorted list, find original index
                                    for (int j = 0; j < childrenCount; j++) {
                                        if (children[childIndex] == mChildren[j]) {
                                            mLastTouchDownIndex = j;
                                            break;
                                        }
                                    }
                                } else {
                                    mLastTouchDownIndex = childIndex;
                                }
                                mLastTouchDownX = ev.getX();
                                mLastTouchDownY = ev.getY();
                                newTouchTarget = addTouchTarget(child, idBitsToAssign);
                                alreadyDispatchedToNewTouchTarget = true;
                                break;
                            }
        }

上面这段代码逻辑也很清晰,首先遍历ViewGroup中的所有子元素,然后判断子元素是否能够接收到点击事件。是否能够接收点击事件由两点来衡量:子元素是否在播动画和点击事件的坐标是否落在子元素的区域内。如果某个子元素满足这两个条件,那么事件就会传递给它处理。
可以看到,dispatchTransformedTouchEvent()实际上调用的就是子元素的dispatchTouchEvent方法,在它的内部有如下一段内容,而在上面的代码中child传递不是null,因此它会直接调用子元素的dispatchTouchEvent方法,这样事件就交由子元素处理了。

private boolean dispatchTransformedTouchEvent(MotionEvent event, boolean cancel,View child, int desiredPointerIdBits) {
        final boolean handled;

        // Canceling motions is a special case.  We don't need to perform any transformations
        // or filtering.  The important part is the action, not the contents.
        final int oldAction = event.getAction();
        if (cancel || oldAction == MotionEvent.ACTION_CANCEL) {
            event.setAction(MotionEvent.ACTION_CANCEL);
            if (child == null) {
                handled = super.dispatchTouchEvent(event);
            } else {
                handled = child.dispatchTouchEvent(event);
            }
            event.setAction(oldAction);
            return handled;
        }

        // Calculate the number of pointers to deliver.
        final int oldPointerIdBits = event.getPointerIdBits();
        final int newPointerIdBits = oldPointerIdBits & desiredPointerIdBits;

        // If for some reason we ended up in an inconsistent state where it looks like we
        // might produce a motion event with no pointers in it, then drop the event.
        if (newPointerIdBits == 0) {
            return false;
        }

        // If the number of pointers is the same and we don't need to perform any fancy
        // irreversible transformations, then we can reuse the motion event for this
        // dispatch as long as we are careful to revert any changes we make.
        // Otherwise we need to make a copy.
        final MotionEvent transformedEvent;
        if (newPointerIdBits == oldPointerIdBits) {
            if (child == null || child.hasIdentityMatrix()) {
                if (child == null) {
                    handled = super.dispatchTouchEvent(event);
                } else {
                    final float offsetX = mScrollX - child.mLeft;
                    final float offsetY = mScrollY - child.mTop;
                    event.offsetLocation(offsetX, offsetY);

                    handled = child.dispatchTouchEvent(event);

                    event.offsetLocation(-offsetX, -offsetY);
                }
                return handled;
            }
            transformedEvent = MotionEvent.obtain(event);
        } else {
            transformedEvent = event.split(newPointerIdBits);
        }

        // Perform any necessary transformations and dispatch.
        if (child == null) {
            handled = super.dispatchTouchEvent(transformedEvent);
        } else {
            final float offsetX = mScrollX - child.mLeft;
            final float offsetY = mScrollY - child.mTop;
            transformedEvent.offsetLocation(offsetX, offsetY);
            if (! child.hasIdentityMatrix()) {
                transformedEvent.transform(child.getInverseMatrix());
            }

            handled = child.dispatchTouchEvent(transformedEvent);
        }

        // Done.
        transformedEvent.recycle();
        return handled;
    }

这个看的脑袋都有点晕了,如果你看到这里了的话。暂时就分析到这吧。

作者:duxingjianghu66 发表于2016/9/11 20:39:38 原文链接
阅读:83 评论:0 查看评论

Android中常见的内存泄漏汇总

$
0
0

Android 内存泄漏总结


集合类泄漏

集合类如果仅仅有添加元素的方法,而没有相应的删除机制,导致内存被占用。如果这个集合类是全局性的变量 (比如类中的静态属性,全局性的 map 等即有静态引用或 final 一直指向它),那么没有相应的删除机制,很可能导致集合所占用的内存只增不减。比如上面的典型例子就是其中一种情况,当然实际上我们在项目中肯定不会写这么 2B 的代码,但稍不注意还是很容易出现这种情况,比如我们都喜欢通过 HashMap 做一些缓存之类的事,这种情况就要多留一些心眼。

单例造成的内存泄漏

由于单例的静态特性使得其生命周期跟应用的生命周期一样长,所以如果使用不恰当的话,很容易造成内存泄漏。比如下面一个典型的例子,

public class AppManager {
private static AppManager instance;
private Context context;
private AppManager(Context context) {
this.context = context;
}
public static AppManager getInstance(Context context) {
if (instance == null) {
instance = new AppManager(context);
}
return instance;
}
}

这是一个普通的单例模式,当创建这个单例的时候,由于需要传入一个Context,所以这个Context的生命周期的长短至关重要:

1、如果此时传入的是 Application 的 Context,因为 Application 的生命周期就是整个应用的生命周期,所以这将没有任何问题。

2、如果此时传入的是 Activity 的 Context,当这个 Context 所对应的 Activity 退出时,由于该 Context 的引用被单例对象所持有,其生命周期等于整个应用程序的生命周期,所以当前 Activity 退出时它的内存并不会被回收,这就造成泄漏了。

正确的方式应该改为下面这种方式:

public class AppManager {
private static AppManager instance;
private Context context;
private AppManager(Context context) {
this.context = context.getApplicationContext();// 使用Application 的context
}
public static AppManager getInstance(Context context) {
if (instance == null) {
instance = new AppManager(context);
}
return instance;
}
}

或者这样写,连 Context 都不用传进来了:

在你的 Application 中添加一个静态方法,getContext() 返回 Application 的 context,

...

context = getApplicationContext();

...
   /**
     * 获取全局的context
     * @return 返回全局context对象
     */
    public static Context getContext(){
        return context;
    }

public class AppManager {
private static AppManager instance;
private Context context;
private AppManager() {
this.context = MyApplication.getContext();// 使用Application 的context
}
public static AppManager getInstance() {
if (instance == null) {
instance = new AppManager();
}
return instance;
}
}

匿名内部类/非静态内部类和异步线程

非静态内部类创建静态实例造成的内存泄漏

有的时候我们可能会在启动频繁的Activity中,为了避免重复创建相同的数据资源,可能会出现这种写法:

        public class MainActivity extends AppCompatActivity {
        private static TestResource mResource = null;
        @Override
        protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        if(mManager == null){
        mManager = new TestResource();
        }
        //...
        }
        class TestResource {
        //...
        }
        }

这样就在Activity内部创建了一个非静态内部类的单例,每次启动Activity时都会使用该单例的数据,这样虽然避免了资源的重复创建,不过这种写法却会造成内存泄漏,因为非静态内部类默认会持有外部类的引用,而该非静态内部类又创建了一个静态的实例,该实例的生命周期和应用的一样长,这就导致了该静态实例一直会持有该Activity的引用,导致Activity的内存资源不能正常回收。正确的做法为:

将该内部类设为静态内部类或将该内部类抽取出来封装成一个单例,如果需要使用Context,请按照上面推荐的使用Application 的 Context。当然,Application 的 context 不是万能的,所以也不能随便乱用,对于有些地方则必须使用 Activity 的 Context,对于Application,Service,Activity三者的Context的应用场景如下:

其中: NO1表示 Application 和 Service 可以启动一个 Activity,不过需要创建一个新的 task 任务队列。而对于 Dialog 而言,只有在 Activity 中才能创建

匿名内部类

android开发经常会继承实现Activity/Fragment/View,此时如果你使用了匿名类,并被异步线程持有了,那要小心了,如果没有任何措施这样一定会导致泄露

    public class MainActivity extends Activity {
    ...
    Runnable ref1 = new MyRunable();
    Runnable ref2 = new Runnable() {
        @Override
        public void run() {

        }
    };
       ...
    }

ref1和ref2的区别是,ref2使用了匿名内部类。我们来看看运行时这两个引用的内存:

可以看到,ref1没什么特别的。

但ref2这个匿名类的实现对象里面多了一个引用:

this$0这个引用指向MainActivity.this,也就是说当前的MainActivity实例会被ref2持有,如果将这个引用再传入一个异步线程,此线程和此Acitivity生命周期不一致的时候,就造成了Activity的泄露。

Handler 造成的内存泄漏

Handler 的使用造成的内存泄漏问题应该说是最为常见了,很多时候我们为了避免 ANR 而不在主线程进行耗时操作,在处理网络任务或者封装一些请求回调等api都借助Handler来处理,但 Handler 不是万能的,对于 Handler 的使用代码编写一不规范即有可能造成内存泄漏。另外,我们知道 Handler、Message 和 MessageQueue 都是相互关联在一起的,万一 Handler 发送的 Message 尚未被处理,则该 Message 及发送它的 Handler 对象将被线程 MessageQueue 一直持有。

由于 Handler 属于 TLS(Thread Local Storage) 变量, 生命周期和 Activity 是不一致的。因此这种实现方式一般很难保证跟 View 或者 Activity 的生命周期保持一致,故很容易导致无法正确释放。

举个例子:

    public class SampleActivity extends Activity {

    private final Handler mLeakyHandler = new Handler() {
    @Override
    public void handleMessage(Message msg) {
      // ...
    }
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    // Post a message and delay its execution for 10 minutes.
    mLeakyHandler.postDelayed(new Runnable() {
      @Override
      public void run() { /* ... */ }
    }, 1000 * 60 * 10);

    // Go back to the previous Activity.
    finish();
    }
    }

在该 SampleActivity 中声明了一个延迟10分钟执行的消息 Message,mLeakyHandler 将其 push 进了消息队列 MessageQueue 里。当该 Activity 被 finish() 掉时,延迟执行任务的 Message 还会继续存在于主线程中,它持有该 Activity 的 Handler 引用,所以此时 finish() 掉的 Activity 就不会被回收了从而造成内存泄漏(因 Handler 为非静态内部类,它会持有外部类的引用,在这里就是指 SampleActivity)。

修复方法:在 Activity 中避免使用非静态内部类,比如上面我们将 Handler 声明为静态的,则其存活期跟 Activity 的生命周期就无关了。同时通过弱引用的方式引入 Activity,避免直接将 Activity 作为 context 传进去,见下面代码:

public class SampleActivity extends Activity {

  /**
   * Instances of static inner classes do not hold an implicit
   * reference to their outer class.
   */
  private static class MyHandler extends Handler {
    private final WeakReference<SampleActivity> mActivity;

    public MyHandler(SampleActivity activity) {
      mActivity = new WeakReference<SampleActivity>(activity);
    }

    @Override
    public void handleMessage(Message msg) {
      SampleActivity activity = mActivity.get();
      if (activity != null) {
        // ...
      }
    }
  }

  private final MyHandler mHandler = new MyHandler(this);

  /**
   * Instances of anonymous classes do not hold an implicit
   * reference to their outer class when they are "static".
   */
  private static final Runnable sRunnable = new Runnable() {
      @Override
      public void run() { /* ... */ }
  };

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    // Post a message and delay its execution for 10 minutes.
    mHandler.postDelayed(sRunnable, 1000 * 60 * 10);

    // Go back to the previous Activity.
    finish();
  }
}

综述,即推荐使用静态内部类 + WeakReference 这种方式。每次使用前注意判空。

前面提到了 WeakReference,所以这里就简单的说一下 Java 对象的几种引用类型。

Java对引用的分类有 Strong reference, SoftReference, WeakReference, PhatomReference 四种。

在Android应用的开发中,为了防止内存溢出,在处理一些占用内存大而且声明周期较长的对象时候,可以尽量应用软引用和弱引用技术。

软/弱引用可以和一个引用队列(ReferenceQueue)联合使用,如果软引用所引用的对象被垃圾回收器回收,Java虚拟机就会把这个软引用加入到与之关联的引用队列中。利用这个队列可以得知被回收的软/弱引用的对象列表,从而为缓冲器清除已失效的软/弱引用。

假设我们的应用会用到大量的默认图片,比如应用中有默认的头像,默认游戏图标等等,这些图片很多地方会用到。如果每次都去读取图片,由于读取文件需要硬件操作,速度较慢,会导致性能较低。所以我们考虑将图片缓存起来,需要的时候直接从内存中读取。但是,由于图片占用内存空间比较大,缓存很多图片需要很多的内存,就可能比较容易发生OutOfMemory异常。这时,我们可以考虑使用软/弱引用技术来避免这个问题发生。以下就是高速缓冲器的雏形:

首先定义一个HashMap,保存软引用对象。

private Map <String, SoftReference<Bitmap>> imageCache = new HashMap <String, SoftReference<Bitmap>> ();

再来定义一个方法,保存Bitmap的软引用到HashMap。

使用软引用以后,在OutOfMemory异常发生之前,这些缓存的图片资源的内存空间可以被释放掉的,从而避免内存达到上限,避免Crash发生。

如果只是想避免OutOfMemory异常的发生,则可以使用软引用。如果对于应用的性能更在意,想尽快回收一些占用内存比较大的对象,则可以使用弱引用。

另外可以根据对象是否经常使用来判断选择软引用还是弱引用。如果该对象可能会经常使用的,就尽量用软引用。如果该对象不被使用的可能性更大些,就可以用弱引用。

ok,继续回到主题。前面所说的,创建一个静态Handler内部类,然后对 Handler 持有的对象使用弱引用,这样在回收时也可以回收 Handler 持有的对象,但是这样做虽然避免了 Activity 泄漏,不过 Looper 线程的消息队列中还是可能会有待处理的消息,所以我们在 Activity 的 Destroy 时或者 Stop 时应该移除消息队列 MessageQueue 中的消息。

下面几个方法都可以移除 Message:

public final void removeCallbacks(Runnable r);

public final void removeCallbacks(Runnable r, Object token);

public final void removeCallbacksAndMessages(Object token);

public final void removeMessages(int what);

public final void removeMessages(int what, Object object);

尽量避免使用 static 成员变量

如果成员变量被声明为 static,那我们都知道其生命周期将与整个app进程生命周期一样。

这会导致一系列问题,如果你的app进程设计上是长驻内存的,那即使app切到后台,这部分内存也不会被释放。按照现在手机app内存管理机制,占内存较大的后台进程将优先回收,yi'wei如果此app做过进程互保保活,那会造成app在后台频繁重启。当手机安装了你参与开发的app以后一夜时间手机被消耗空了电量、流量,你的app不得不被用户卸载或者静默。

这里修复的方法是:

不要在类初始时初始化静态成员。可以考虑lazy初始化。架构设计上要思考是否真的有必要这样做,尽量避免。如果架构需要这么设计,那么此对象的生命周期你有责任管理起来。

避免 override finalize()

1、finalize 方法被执行的时间不确定,不能依赖与它来释放紧缺的资源。时间不确定的原因是: 虚拟机调用GC的时间不确定 Finalize daemon线程被调度到的时间不确定

2、finalize 方法只会被执行一次,即使对象被复活,如果已经执行过了 finalize 方法,再次被 GC 时也不会再执行了,原因是:

含有 finalize 方法的 object 是在 new 的时候由虚拟机生成了一个 finalize reference 在来引用到该Object的,而在 finalize 方法执行的时候,该 object 所对应的 finalize Reference 会被释放掉,即使在这个时候把该 object 复活(即用强引用引用住该 object ),再第二次被 GC 的时候由于没有了 finalize reference 与之对应,所以 finalize 方法不会再执行。

3、含有Finalize方法的object需要至少经过两轮GC才有可能被释放。

资源未关闭造成的内存泄漏

对于使用了BraodcastReceiver,ContentObserver,File,游标 Cursor,Stream,Bitmap等资源的使用,应该在Activity销毁时及时关闭或者注销,否则这些资源将不会被回收,造成内存泄漏。

一些不良代码造成的内存压力

有些代码并不造成内存泄露,但是它们,或是对没使用的内存没进行有效及时的释放,或是没有有效的利用已有的对象而是频繁的申请新内存。

比如: Bitmap 没调用 recycle()方法,对于 Bitmap 对象在不使用时,我们应该先调用 recycle() 释放内存,然后才它设置为 null. 因为加载 Bitmap 对象的内存空间,一部分是 java 的,一部分 C 的(因为 Bitmap 分配的底层是通过 JNI 调用的 )。 而这个 recyle() 就是针对 C 部分的内存释放。 构造 Adapter 时,没有使用缓存的 convertView ,每次都在创建新的 converView。这里推荐使用 ViewHolder。

总结

对 Activity 等组件的引用应该控制在 Activity 的生命周期之内; 如果不能就考虑使用 getApplicationContext 或者 getApplication,以避免 Activity 被外部长生命周期的对象引用而泄露。

尽量不要在静态变量或者静态内部类中使用非静态外部成员变量(包括context ),即使要使用,也要考虑适时把外部成员变量置空;也可以在内部类中使用弱引用来引用外部类的变量。

对于生命周期比Activity长的内部类对象,并且内部类中使用了外部类的成员变量,可以这样做避免内存泄漏:

    将内部类改为静态内部类
    静态内部类中使用弱引用来引用外部类的成员变量

Handler 的持有的引用对象最好使用弱引用,资源释放时也可以清空 Handler 里面的消息。比如在 Activity onStop 或者 onDestroy 的时候,取消掉该 Handler 对象的 Message和 Runnable.

在 Java 的实现过程中,也要考虑其对象释放,最好的方法是在不使用某对象时,显式地将此对象赋值为 null,比如使用完Bitmap 后先调用 recycle(),再赋为null,清空对图片等资源有直接引用或者间接引用的数组(使用 array.clear() ; array = null)等,最好遵循谁创建谁释放的原则。

正确关闭资源,对于使用了BraodcastReceiver,ContentObserver,File,游标 Cursor,Stream,Bitmap等资源的使用,应该在Activity销毁时及时关闭或者注销。

保持对对象生命周期的敏感,特别注意单例、静态对象、全局性集合等的生命周期。


作者:shangzhongjia 发表于2016/9/11 20:47:46 原文链接
阅读:86 评论:0 查看评论

论字母导航的重要性,我们来实现一个联系人字母导航列表吧!

$
0
0

论字母导航的重要性,我们来实现一个联系人字母导航列表吧!


说起这个字母导航,我相信大家都不陌生,不论是联系人列表还是城市列表,基本上都是需要字母导航,那我们就有必要来研究一下这个思路的探索了,毕竟这是一个非常常用的功能,如果现在把轮子造好,那以后也可以节省很多的时间,同时,我们把思路理清楚了,对我们以后的帮助也是很大的,那好,既然如此,我们就一起来探索一下吧!

这里写图片描述

我们首选新建一个项目——LettersNavigation

这里写图片描述

OK,工程建立好之后我们来思考一下这个功能的一个实现逻辑

这里写图片描述

逻辑不是很难,那我们首先要去做的就是把大致的框架搭好,也就是布局,我们来看

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <!--搜索框-->
    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginLeft="5dp"
        android:layout_marginRight="5dp"
        android:layout_marginTop="5dp"
        android:alpha="0.5"
        android:background="@drawable/search_bg">

        <ImageView
            android:id="@+id/iv_search"
            android:layout_width="50dp"
            android:layout_height="50dp"
            android:src="@drawable/ic_search"/>

        <EditText
            android:layout_width="match_parent"
            android:layout_height="50dp"
            android:layout_alignParentTop="true"
            android:layout_marginRight="10dp"
            android:layout_toRightOf="@+id/iv_search"
            android:background="@null"
            android:hint="请输入联系人"
            android:singleLine="true"
            android:textColor="@android:color/white"
            android:textColorHint="@android:color/white"/>

        <ImageView
            android:layout_width="30dp"
            android:layout_height="30dp"
            android:layout_alignParentRight="true"
            android:layout_centerVertical="true"
            android:layout_marginRight="10dp"
            android:src="@drawable/titlebar_cancel"
            android:visibility="gone"/>
    </RelativeLayout>

    <!--列表-->
    <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <ListView
            android:id="@+id/mListView"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:divider="@null"/>

        <!--字母提示-->
        <TextView
            android:id="@+id/tvToast"
            android:layout_width="100dp"
            android:layout_height="100dp"
            android:layout_gravity="center"
            android:alpha="0.5"
            android:background="@drawable/toast_bg"
            android:gravity="center"
            android:text="A"
            android:textColor="@android:color/white"
            android:textSize="25sp"
            android:visibility="gone"/>

        <!--字母导航-->
        <com.liuguilin.lettersnavigation.view.LettersView
            android:layout_width="20dp"
            android:layout_height="match_parent"
            android:layout_gravity="right"/>

    </FrameLayout>

</LinearLayout>

这里就比较好理解了,首选是最上面的一个搜索框,我们监听里面的内容,有内容的haunted我就显示清除按钮,下面是一个FrameLayout,他包裹着一个ListView显示联系人,一个TextView是作为字母提示的,最右边就是我们的自定义字母导航栏LettersView了,同样的,因为主页有输入框,他只要一进去就会获取到焦点弹起输入法,这样的交互式不友好的,我们在清单文件中的Activity根节点加一个属性

 android:windowSoftInputMode="adjustUnspecified|stateHidden"

还有我们搜索的输入框的背景,因为我没有找到合适的.9图片,PS也不是很懂,就自己绘制了一个圆角的背景

search_bg.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
    <solid android:color="@color/colorPrimary"/>
    <corners android:radius="20dp"/>

</shape>

同理,还有我们字母提示TextView的背景

toast_bg.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
    <solid android:color="@android:color/black"/>
    <corners android:radius="10dp"/>

</shape>

在我看来,xml绘制动画也好,显示效果也好,都是十分的方便的,这个一定要掌握以下哦!,好的,前期的架子搭完了,我们现在可以重点来看一下这个字母View了,其实他就两个步骤,在我看来,首先绘制这个View,然后通过手势监听去逐帧他的选中字母,拿这样的话,我们的绘制应该是这个样子的:

    /**
     * 绘制
     *
     * @param canvas
     */
    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        /**
         * 为了排列26个字母,我们可以用坐标点来计算,X居中,Y为 1/27 的递加计算
         * 首先获取到我们View的宽高
         */
        int viewWidth = getWidth();
        int viewHeight = getHeight();
        //计算一个字母的高度
        int singleHeight = viewHeight / strChars.length;
        //循环绘制字母
        for (int i = 0; i < strChars.length; i++) {
            //设置选中字母的颜色
            if (i == checkIndex) {
                mPaint.setColor(Color.BLACK);
                mPaint.setTextSize(50);
            } else {
                mPaint.setColor(Color.WHITE);
                //设置字体大小
                mPaint.setTextSize(40);
            }
            /**
             * 绘制字母
             * x: (view的宽度 - 文本的宽度)/ 2
             * y:  singleHeight * x + singleHeight  //单个字母的高度 + 最上面的字幕空白高度
             */
            float lettersX = (viewWidth - mPaint.measureText(strChars[i])) / 2;
            float lettersY = singleHeight * i + singleHeight;
            //绘制
            canvas.drawText(strChars[i], lettersX, lettersY, mPaint);
            //重绘
            mPaint.reset();
        }
    }

然后我们就可以来预览以下效果了

这里写图片描述

感觉还是有点挫呀,不过先不管,我们仔细看下这个onDraw方法,其实我们主要还是计算x,y的坐标然后去绘制,在绘制的时候我们定义一个选中的下标,,默认为0,所以默认选中A,好的,那我们再来实现手势的监听吧!这里我们用事件分发来做是最合适的了

    /**
     * 事件分发
     *
     * @param event
     * @return
     */
    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {
        //判断手势
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
            case MotionEvent.ACTION_MOVE:
                setBackgroundResource(R.color.colorAccent);
                //获取点击的Y坐标,以此来判断选中的字母
                float y = event.getY();
                Log.i(TAG, "y:" + y);
                //第一次被选中的下标
                int oldCheckIndex = checkIndex;
                /**
                 * 计算选中的字母
                 * strChars[当前Y / View的高度 * 字母个数]
                 */
                int c = (int) (y / getHeight() * strChars.length);
                Log.i(TAG, "c:" + c);
                //判断移动
                if (oldCheckIndex != c) {
                    //不能越界
                    if (c >= 0 && c < strChars.length) {
                        if (mTextView != null) {
                            mTextView.setVisibility(View.VISIBLE);
                            mTextView.setText(strChars[c]);
                        }
                    }
                    checkIndex = c;
                    invalidate();
                }
                break;
            case MotionEvent.ACTION_UP:
                //设置透明背景
                setBackgroundResource(android.R.color.transparent);
                //恢复不选中
                checkIndex = -1;
                invalidate();
                //是否显示
                if (mTextView != null) {
                    mTextView.setVisibility(View.INVISIBLE);
                }
                break;
        }
        return true;
    }

其实这里也是比较简单的,不过这里有一个set/get的TextView,需要在MainActivity里面去设置一下

 mLettersView = (LettersView) findViewById(R.id.mLettersView);
 mLettersView.setmTextView(tvToast);

这样我们就可以看到实际的效果了

这里写图片描述

这个View当然不止做这么一点点事情了,我们等下还需要他与ListView去联动呢,那既然如此,我们先把ListView给撸出来,这个ListView其实很简单,不要看我们的不规则排列,其实他的原理就是item上有两个TextView,上面是字母,下面是姓名,当然,我们要去转换判断一下并且计算出谁该显示字母,谁有需要去隐藏,所以我们的item应该是

list_item.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <TextView
        android:layout_marginLeft="10dp"
        android:id="@+id/tvLetters"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="A"
        android:textColor="@color/colorAccent"
        android:textSize="20sp"/>

    <TextView
        android:layout_marginLeft="10dp"
        android:id="@+id/tvName"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="5dp"
        android:text="阿三"
        android:textSize="16sp"/>

</LinearLayout>

然后就是我们的实体类了

LettersModel

package com.liuguilin.lettersnavigation.entity;

/*
 *  项目名:  LettersNavigation 
 *  包名:    com.liuguilin.lettersnavigation.entity
 *  文件名:   LettersModel
 *  创建者:   LGL
 *  创建时间:  2016/9/11 16:55
 *  描述:    联系人实体
 */

public class LettersModel {

    //字母
    private String letter;
    //联系人
    private String name;

    public String getLetter() {
        return letter;
    }

    public void setLetter(String letter) {
        this.letter = letter;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

当然,我们又两个重要的环节,一个是数据,还有一个适配器,我们先来看下数据怎么去用,首先我们模拟一些数据

//联系人数据模拟
private String[] strName = {"张三", "李四", "李七", "刘某人", "王五", "Android", "IOS", "王寡妇","阿三", "爸爸", "妈妈", "CoCo", "弟弟", "尔康", "紫薇", "小燕子", "皇阿玛", "福尔康", "哥哥", "Hi", "I", "杰克", "克星", "乐乐", "你好", "Oppo", "皮特", "曲奇饼","日啊", "思思", "缇娜", "U", "V", "王大叔", "嘻嘻", "一小伙子", "撒贝宁", "吱吱", "舅舅", "老总", "隔壁老王", "许仙"};

然后我们写个方法

    /**
     * 联系人数组转换实体数据
     *
     * @return
     */
    private List<LettersModel> parsingData() {
        List<LettersModel> listModel = new ArrayList<>();
        Log.i(TAG, " strName.length:" + strName.length);
        for (int i = 0; i < strName.length; i++) {
            LettersModel model = new LettersModel();
            model.setName(strName[i]);
            Log.i(TAG, strName[i]);
            //转换拼音截取首字母并且大写
            String pinyin = Trans2PinYin.trans2PinYin(strName[i]);
            Log.i(TAG, "pinyin:" + pinyin);
            String letter = pinyin.substring(0, 1).toUpperCase();
            Log.i(TAG, "letter:" + letter);
            model.setLetter(letter);
            listModel.add(model);
        }
        return listModel;
    }

这个方法主要是把数据填充到我们的数据集里面,然后我们就要进行排序了,我们排序的规则是A-Z #,那我们就得自定义一个排序规则

LettersSorting

package com.liuguilin.lettersnavigation.utils;

/*
 *  项目名:  LettersNavigation 
 *  包名:    com.liuguilin.lettersnavigation.utils
 *  文件名:   LettersSorting
 *  创建者:   LGL
 *  创建时间:  2016/9/11 18:04
 *  描述:    字母排序算法
 */

import com.liuguilin.lettersnavigation.entity.LettersModel;

import java.util.Comparator;

public class LettersSorting implements Comparator<LettersModel> {

    @Override
    public int compare(LettersModel lettersModel, LettersModel t1) {
        //给我两个对象,我只比较他的字母
        return lettersModel.getLetter().compareTo(t1.getLetter());
    }
}

这样我们就可以调通了,我把MainActivity的代码全部贴上你就能看的十分的清晰了

MainActivity

package com.liuguilin.lettersnavigation;

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.TextView;

import com.liuguilin.lettersnavigation.adapter.LettersAdapter;
import com.liuguilin.lettersnavigation.entity.LettersModel;
import com.liuguilin.lettersnavigation.utils.LettersSorting;
import com.liuguilin.lettersnavigation.utils.Trans2PinYin;
import com.liuguilin.lettersnavigation.view.LettersView;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

public class MainActivity extends AppCompatActivity {

    //TAG
    private static final String TAG = "Letters";

    //联系人列表
    private ListView mListView;
    //字母提示
    private TextView tvToast;
    //字母列表
    private LettersView mLettersView;
    //搜索框
    private EditText et_search;
    //列表数据
    private List<LettersModel> mList = new ArrayList<>();
    //数据源
    private LettersAdapter adapter;
    //联系人数据模拟
    private String[] strName = {"张三", "李四", "李七", "刘某人", "王五", "Android", "IOS", "王寡妇","阿三", "爸爸", "妈妈", "CoCo", "弟弟", "尔康", "紫薇", "小燕子", "皇阿玛", "福尔康", "哥哥", "Hi", "I", "杰克", "克星", "乐乐", "你好", "Oppo", "皮特", "曲奇饼","日啊", "思思", "缇娜", "U", "V", "王大叔", "嘻嘻", "一小伙子", "撒贝宁", "吱吱", "舅舅", "老总", "隔壁老王", "许仙"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initView();
    }

    /**
     * 初始化View
     */
    private void initView() {
        mListView = (ListView) findViewById(R.id.mListView);
        tvToast = (TextView) findViewById(R.id.tvToast);
        et_search = (EditText) findViewById(R.id.et_search);
        mLettersView = (LettersView) findViewById(R.id.mLettersView);
        mLettersView.setmTextView(tvToast);

        //加载联系人的模拟数据
        mList = parsingData();
        //对字母进行排序A-Z #
        Collections.sort(mList, new LettersSorting());
        //加载适配器
        adapter = new LettersAdapter(this, mList);
        //设置数据
        mListView.setAdapter(adapter);
    }

    /**
     * 联系人数组转换实体数据
     *
     * @return
     */
    private List<LettersModel> parsingData() {
        List<LettersModel> listModel = new ArrayList<>();
        Log.i(TAG, " strName.length:" + strName.length);
        for (int i = 0; i < strName.length; i++) {
            LettersModel model = new LettersModel();
            model.setName(strName[i]);
            Log.i(TAG, strName[i]);
            //转换拼音截取首字母并且大写
            String pinyin = Trans2PinYin.trans2PinYin(strName[i]);
            Log.i(TAG, "pinyin:" + pinyin);
            String letter = pinyin.substring(0, 1).toUpperCase();
            Log.i(TAG, "letter:" + letter);
            model.setLetter(letter);
            listModel.add(model);
        }
        return listModel;
    }
}

OK,正如你所见,我们最重要的是LettersAdapter,我们先来分析一下这个adapter,其实他要做的就两件事情,首选把字母的第一个排出来,然后依次显示数据,我们直接看代码

LettersAdapter

package com.liuguilin.lettersnavigation.adapter;

/*
 *  项目名:  LettersNavigation 
 *  包名:    com.liuguilin.lettersnavigation.adapter
 *  文件名:   LettersAdapter
 *  创建者:   LGL
 *  创建时间:  2016/9/11 18:12
 *  描述:    联系人适配器
 */

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.TextView;

import com.liuguilin.lettersnavigation.R;
import com.liuguilin.lettersnavigation.entity.LettersModel;

import java.util.List;

public class LettersAdapter extends BaseAdapter {

    //上下文
    private Context mContext;
    //数据集
    private List<LettersModel> mList;
    //布局加载器
    private LayoutInflater mInflater;
    //实体类
    private LettersModel model;

    public LettersAdapter(Context mContext, List<LettersModel> mList) {
        this.mContext = mContext;
        this.mList = mList;

        //获取系统服务
        mInflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    }

    @Override
    public int getCount() {
        return mList.size();
    }

    @Override
    public Object getItem(int i) {
        return mList.get(i);
    }

    @Override
    public long getItemId(int i) {
        return i;
    }

    @Override
    public View getView(int i, View view, ViewGroup viewGroup) {
        ViewHolder vHolder = null;
        if (view == null) {
            vHolder = new ViewHolder();
            //加载布局
            view = mInflater.inflate(R.layout.list_item, null);
            vHolder.tvLetters = (TextView) view.findViewById(R.id.tvLetters);
            vHolder.tvName = (TextView) view.findViewById(R.id.tvName);
            view.setTag(vHolder);
        } else {
            vHolder = (ViewHolder) view.getTag();
        }
        //选中下标
        model = mList.get(i);
        //获取首字母显示人
        int firstPosition = getNmaeForPosition(i);
        //第一个
        int index = getPositionForNmae(firstPosition);
        //需要显示字母
        if (index == i) {
            vHolder.tvLetters.setVisibility(View.VISIBLE);
            vHolder.tvLetters.setText(model.getLetter());
        } else {
            vHolder.tvLetters.setVisibility(View.GONE);
        }
        vHolder.tvName.setText(model.getName());
        return view;
    }

    /**
     * 缓存优化
     */
    class ViewHolder {
        private TextView tvLetters;
        private TextView tvName;
    }

    /**
     * 通过首字母获取该首字母要显示的第一个人的下标
     *
     * @param position
     * @return
     */
    private int getPositionForNmae(int position) {
        for (int i = 0; i < getCount(); i++) {
            String letter = mList.get(i).getLetter();
            //首字母显示
            char firstChar = letter.toUpperCase().charAt(0);
            if (firstChar == position) {
                return i;
            }
        }
        return -1;
    }

    /**
     * 根据名称拿到下标
     *
     * @param position
     * @return
     */
    private int getNmaeForPosition(int position) {
        return mList.get(position).getLetter().charAt(0);
    }

}

这里最关键的也就在于getPositionForNmae方法他直接计算出了我们一堆同类型的联系人中的第一个数据并且返回出来,然后我们再利用getNmaeForPosition拿到需要显示的position,OK,到这里,我们基本上就可以看到很大一部分效果了

这里写图片描述

现在这个大体的架构就已经搭建出来了,我们现在最后的难点就是如何字母导航和ListView的联动了,我们只能回到我们的LettersView,其实这个说难也不难,主要还是一个思想,我们可以用接口的形式去做,首先我们定义一个接口

  /**
     * 接口回调/ListView联动
     */
    public interface OnLettersListViewListener {
        public void onLettersListener(String s);
    }

并且实现它的set/get方法,然后我们在选中的手势事件中,我们去直接设置

 //效果联动
 if (onLettersListViewListener != null) {
      onLettersListViewListener.onLettersListener(strChars[c]);
 }

这里我们回传回去的是我们选中的字母,我们再回到我们的MainActivity,然后直接

implements LettersView.OnLettersListViewListener

设置了我们的监听之后,我们可以直接移动

    /**
     * ListView与字母导航联动
     *
     * @param s
     */
    @Override
    public void onLettersListener(String s) {
        //对应的位置
        int position = adapter.getPositionForNmae(s.charAt(0));
        //移动
        mListView.setSelection(position);
    }

我们可以来看一下最终的效果

这里写图片描述

现在思路是不是一场的清晰?这里我把这个View的代码贴上

LettersView

package com.liuguilin.lettersnavigation.view;

/*
 *  项目名:  LettersNavigation 
 *  包名:    com.liuguilin.lettersnavigation.view
 *  文件名:   LettersView
 *  创建者:   LGL
 *  创建时间:  2016/9/11 11:58
 *  描述:    字母导航
 */

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Typeface;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.widget.TextView;

import com.liuguilin.lettersnavigation.R;

public class LettersView extends View {

    //TAG
    private static final String TAG = "LettersView";

    //字母数组,#代表未知,比如数字开头
    private String[] strChars = {"A", "B", "C", "D", "E", "F", "G", "H", "I", "J",
            "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", "#"};
    //画笔
    private Paint mPaint;
    //选中字母的下标
    private int checkIndex;
    //字母提示的TextView,需要set/get动态设置显示内容
    private TextView mTextView;
    //接口回调
    private OnLettersListViewListener onLettersListViewListener;

    public LettersView(Context context) {
        super(context);
        init();
    }

    public LettersView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public LettersView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    /**
     * 初始化
     */
    private void init() {
        //实例化画笔
        mPaint = new Paint();
        //设置style
        mPaint.setTypeface(Typeface.DEFAULT_BOLD);
        //设置抗锯齿
        mPaint.setAntiAlias(true);
    }

    /**
     * 绘制
     *
     * @param canvas
     */
    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        /**
         * 为了排列26个字母,我们可以用坐标点来计算,X居中,Y为 1/27 的递加计算
         * 首先获取到我们View的宽高
         */
        int viewWidth = getWidth();
        int viewHeight = getHeight();
        //计算一个字母的高度
        int singleHeight = viewHeight / strChars.length;
        //循环绘制字母
        for (int i = 0; i < strChars.length; i++) {
            //设置选中字母的颜色
            if (i == checkIndex) {
                mPaint.setColor(Color.WHITE);
                mPaint.setTextSize(50);
            } else {
                mPaint.setColor(Color.BLACK);
                //设置字体大小
                mPaint.setTextSize(40);
            }
            /**
             * 绘制字母
             * x: (view的宽度 - 文本的宽度)/ 2
             * y:  singleHeight * x + singleHeight  //单个字母的高度 + 最上面的字幕空白高度
             */
            float lettersX = (viewWidth - mPaint.measureText(strChars[i])) / 2;
            float lettersY = singleHeight * i + singleHeight;
            //绘制
            canvas.drawText(strChars[i], lettersX, lettersY, mPaint);
            //重绘
            mPaint.reset();
        }
    }

    public TextView getmTextView() {
        return mTextView;
    }

    public void setmTextView(TextView mTextView) {
        this.mTextView = mTextView;
    }

    /**
     * 事件分发
     *
     * @param event
     * @return
     */
    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {
        //判断手势
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
            case MotionEvent.ACTION_MOVE:
                setBackgroundResource(R.color.colorAccent);
                //获取点击的Y坐标,以此来判断选中的字母
                float y = event.getY();
                Log.i(TAG, "y:" + y);
                //第一次被选中的下标
                int oldCheckIndex = checkIndex;
                /**
                 * 计算选中的字母
                 * strChars[当前Y / View的高度 * 字母个数]
                 */
                int c = (int) (y / getHeight() * strChars.length);
                Log.i(TAG, "c:" + c);
                //判断移动
                if (oldCheckIndex != c) {
                    //不能越界
                    if (c >= 0 && c < strChars.length) {
                        //效果联动
                        if (onLettersListViewListener != null) {
                            onLettersListViewListener.onLettersListener(strChars[c]);
                        }
                        if (mTextView != null) {
                            mTextView.setVisibility(View.VISIBLE);
                            mTextView.setText(strChars[c]);
                        }
                    }
                    checkIndex = c;
                    invalidate();
                }
                break;
            case MotionEvent.ACTION_UP:
                //设置透明背景
                setBackgroundResource(android.R.color.transparent);
                //恢复不选中
                checkIndex = -1;
                invalidate();
                //是否显示
                if (mTextView != null) {
                    mTextView.setVisibility(View.INVISIBLE);
                }
                break;
        }
        return true;
    }

    public OnLettersListViewListener getOnLettersListViewListener() {
        return onLettersListViewListener;
    }

    public void setOnLettersListViewListener(OnLettersListViewListener onLettersListViewListener) {
        this.onLettersListViewListener = onLettersListViewListener;
    }

    /**
     * 接口回调/ListView联动
     */
    public interface OnLettersListViewListener {
        public void onLettersListener(String s);
    }
}

ok,这里最终小伙伴是不是还有一个疑问,就是我们使用到的Trans2PinYin这个类是什么?事实上,这个类的唯一功能就是把汉子转化成拼音的工具类,在android官方的通讯录中就有这个类,有兴趣的可以去看一下源码,最后我把这个类的源码贴上:

Trans2PinYin

package com.liuguilin.lettersnavigation.utils;

/*
 *  项目名:  HanZiToPinYinSample 
 *  包名:    com.liuguilin.hanzitopinyinsample
 *  文件名:   Trans2PinYin
 *  创建者:   LGL
 *  创建时间:  2016/8/23 17:05
 *  描述:    汉字转拼音
 */

public class Trans2PinYin {

    private static int[] pyvalue = new int[]{-20319, -20317, -20304, -20295,
            -20292, -20283, -20265, -20257, -20242, -20230, -20051, -20036,
            -20032, -20026, -20002, -19990, -19986, -19982, -19976, -19805,
            -19784, -19775, -19774, -19763, -19756, -19751, -19746, -19741,
            -19739, -19728, -19725, -19715, -19540, -19531, -19525, -19515,
            -19500, -19484, -19479, -19467, -19289, -19288, -19281, -19275,
            -19270, -19263, -19261, -19249, -19243, -19242, -19238, -19235,
            -19227, -19224, -19218, -19212, -19038, -19023, -19018, -19006,
            -19003, -18996, -18977, -18961, -18952, -18783, -18774, -18773,
            -18763, -18756, -18741, -18735, -18731, -18722, -18710, -18697,
            -18696, -18526, -18518, -18501, -18490, -18478, -18463, -18448,
            -18447, -18446, -18239, -18237, -18231, -18220, -18211, -18201,
            -18184, -18183, -18181, -18012, -17997, -17988, -17970, -17964,
            -17961, -17950, -17947, -17931, -17928, -17922, -17759, -17752,
            -17733, -17730, -17721, -17703, -17701, -17697, -17692, -17683,
            -17676, -17496, -17487, -17482, -17468, -17454, -17433, -17427,
            -17417, -17202, -17185, -16983, -16970, -16942, -16915, -16733,
            -16708, -16706, -16689, -16664, -16657, -16647, -16474, -16470,
            -16465, -16459, -16452, -16448, -16433, -16429, -16427, -16423,
            -16419, -16412, -16407, -16403, -16401, -16393, -16220, -16216,
            -16212, -16205, -16202, -16187, -16180, -16171, -16169, -16158,
            -16155, -15959, -15958, -15944, -15933, -15920, -15915, -15903,
            -15889, -15878, -15707, -15701, -15681, -15667, -15661, -15659,
            -15652, -15640, -15631, -15625, -15454, -15448, -15436, -15435,
            -15419, -15416, -15408, -15394, -15385, -15377, -15375, -15369,
            -15363, -15362, -15183, -15180, -15165, -15158, -15153, -15150,
            -15149, -15144, -15143, -15141, -15140, -15139, -15128, -15121,
            -15119, -15117, -15110, -15109, -14941, -14937, -14933, -14930,
            -14929, -14928, -14926, -14922, -14921, -14914, -14908, -14902,
            -14894, -14889, -14882, -14873, -14871, -14857, -14678, -14674,
            -14670, -14668, -14663, -14654, -14645, -14630, -14594, -14429,
            -14407, -14399, -14384, -14379, -14368, -14355, -14353, -14345,
            -14170, -14159, -14151, -14149, -14145, -14140, -14137, -14135,
            -14125, -14123, -14122, -14112, -14109, -14099, -14097, -14094,
            -14092, -14090, -14087, -14083, -13917, -13914, -13910, -13907,
            -13906, -13905, -13896, -13894, -13878, -13870, -13859, -13847,
            -13831, -13658, -13611, -13601, -13406, -13404, -13400, -13398,
            -13395, -13391, -13387, -13383, -13367, -13359, -13356, -13343,
            -13340, -13329, -13326, -13318, -13147, -13138, -13120, -13107,
            -13096, -13095, -13091, -13076, -13068, -13063, -13060, -12888,
            -12875, -12871, -12860, -12858, -12852, -12849, -12838, -12831,
            -12829, -12812, -12802, -12607, -12597, -12594, -12585, -12556,
            -12359, -12346, -12320, -12300, -12120, -12099, -12089, -12074,
            -12067, -12058, -12039, -11867, -11861, -11847, -11831, -11798,
            -11781, -11604, -11589, -11536, -11358, -11340, -11339, -11324,
            -11303, -11097, -11077, -11067, -11055, -11052, -11045, -11041,
            -11038, -11024, -11020, -11019, -11018, -11014, -10838, -10832,
            -10815, -10800, -10790, -10780, -10764, -10587, -10544, -10533,
            -10519, -10331, -10329, -10328, -10322, -10315, -10309, -10307,
            -10296, -10281, -10274, -10270, -10262, -10260, -10256, -10254};
    private static String[] pystr = new String[]{"a", "ai", "an", "ang",
            "ao", "ba", "bai", "ban", "bang", "bao", "bei", "ben", "beng",
            "bi", "bian", "biao", "bie", "bin", "bing", "bo", "bu", "ca",
            "cai", "can", "cang", "cao", "ce", "ceng", "cha", "chai", "chan",
            "chang", "chao", "che", "chen", "cheng", "chi", "chong", "chou",
            "chu", "chuai", "chuan", "chuang", "chui", "chun", "chuo", "ci",
            "cong", "cou", "cu", "cuan", "cui", "cun", "cuo", "da", "dai",
            "dan", "dang", "dao", "de", "deng", "di", "dian", "diao", "die",
            "ding", "diu", "dong", "dou", "du", "duan", "dui", "dun", "duo",
            "e", "en", "er", "fa", "fan", "fang", "fei", "fen", "feng", "fo",
            "fou", "fu", "ga", "gai", "gan", "gang", "gao", "ge", "gei", "gen",
            "geng", "gong", "gou", "gu", "gua", "guai", "guan", "guang", "gui",
            "gun", "guo", "ha", "hai", "han", "hang", "hao", "he", "hei",
            "hen", "heng", "hong", "hou", "hu", "hua", "huai", "huan", "huang",
            "hui", "hun", "huo", "ji", "jia", "jian", "jiang", "jiao", "jie",
            "jin", "jing", "jiong", "jiu", "ju", "juan", "jue", "jun", "ka",
            "kai", "kan", "kang", "kao", "ke", "ken", "keng", "kong", "kou",
            "ku", "kua", "kuai", "kuan", "kuang", "kui", "kun", "kuo", "la",
            "lai", "lan", "lang", "lao", "le", "lei", "leng", "li", "lia",
            "lian", "liang", "liao", "lie", "lin", "ling", "liu", "long",
            "lou", "lu", "lv", "luan", "lue", "lun", "luo", "ma", "mai", "man",
            "mang", "mao", "me", "mei", "men", "meng", "mi", "mian", "miao",
            "mie", "min", "ming", "miu", "mo", "mou", "mu", "na", "nai", "nan",
            "nang", "nao", "ne", "nei", "nen", "neng", "ni", "nian", "niang",
            "niao", "nie", "nin", "ning", "niu", "nong", "nu", "nv", "nuan",
            "nue", "nuo", "o", "ou", "pa", "pai", "pan", "pang", "pao", "pei",
            "pen", "peng", "pi", "pian", "piao", "pie", "pin", "ping", "po",
            "pu", "qi", "qia", "qian", "qiang", "qiao", "qie", "qin", "qing",
            "qiong", "qiu", "qu", "quan", "que", "qun", "ran", "rang", "rao",
            "re", "ren", "reng", "ri", "rong", "rou", "ru", "ruan", "rui",
            "run", "ruo", "sa", "sai", "san", "sang", "sao", "se", "sen",
            "seng", "sha", "shai", "shan", "shang", "shao", "she", "shen",
            "sheng", "shi", "shou", "shu", "shua", "shuai", "shuan", "shuang",
            "shui", "shun", "shuo", "si", "song", "sou", "su", "suan", "sui",
            "sun", "suo", "ta", "tai", "tan", "tang", "tao", "te", "teng",
            "ti", "tian", "tiao", "tie", "ting", "tong", "tou", "tu", "tuan",
            "tui", "tun", "tuo", "wa", "wai", "wan", "wang", "wei", "wen",
            "weng", "wo", "wu", "xi", "xia", "xian", "xiang", "xiao", "xie",
            "xin", "xing", "xiong", "xiu", "xu", "xuan", "xue", "xun", "ya",
            "yan", "yang", "yao", "ye", "yi", "yin", "ying", "yo", "yong",
            "you", "yu", "yuan", "yue", "yun", "za", "zai", "zan", "zang",
            "zao", "ze", "zei", "zen", "zeng", "zha", "zhai", "zhan", "zhang",
            "zhao", "zhe", "zhen", "zheng", "zhi", "zhong", "zhou", "zhu",
            "zhua", "zhuai", "zhuan", "zhuang", "zhui", "zhun", "zhuo", "zi",
            "zong", "zou", "zu", "zuan", "zui", "zun", "zuo"};
    private StringBuilder buffer;
    private String resource;
    private static Trans2PinYin chineseSpelling = new Trans2PinYin();

    public static Trans2PinYin getInstance() {
        return chineseSpelling;
    }

    public String getResource() {
        return resource;
    }

    public void setResource(String resource) {
        this.resource = resource;
    }

    private int getChsAscii(String chs) {
        int asc = 0;
        try {
            byte[] bytes = chs.getBytes("gb2312");
            if (bytes == null || bytes.length > 2 || bytes.length <= 0) { // 错误
                // log
                throw new RuntimeException("illegal resource string");
                // System.out.println("error");
            }
            if (bytes.length == 1) { // 英文字符
                asc = bytes[0];
            }
            if (bytes.length == 2) { // 中文字符
                int hightByte = 256 + bytes[0];
                int lowByte = 256 + bytes[1];
                asc = (256 * hightByte + lowByte) - 256 * 256;
            }
        } catch (Exception e) {
            System.out
                    .println("ERROR:ChineseSpelling.class-getChsAscii(String chs)"
                            + e);
            // e.printStackTrace();
        }
        return asc;
    }

    /**
     * 转换单个汉字
     *
     * @param str
     * @return
     */
    public String convert(String str) {
        String result = null;
        int ascii = getChsAscii(str);
        if (ascii > 0 && ascii < 160) {
            result = String.valueOf((char) ascii);
        } else {
            for (int i = (pyvalue.length - 1); i >= 0; i--) {
                if (pyvalue[i] <= ascii) {
                    result = pystr[i];
                    break;
                }
            }
        }
        return result;
    }

    /**
     * 转换一个或多个汉字
     *
     * @param str
     * @return
     */
    public String convertAll(String str) {
        String result = "";
        String strTemp = null;
        for (int j = 0; j < str.length(); j++) {
            strTemp = str.substring(j, j + 1);
            int ascii = getChsAscii(strTemp);
            if (ascii > 0 && ascii < 160) {
                result += String.valueOf((char) ascii);
            } else {
                for (int i = (pyvalue.length - 1); i >= 0; i--) {
                    if (pyvalue[i] <= ascii) {
                        result += pystr[i];
                        break;
                    }
                }
            }
        }
        return result;
    }

    public String getSelling(String chs) {
        String key, value;
        buffer = new StringBuilder();
        for (int i = 0; i < chs.length(); i++) {
            key = chs.substring(i, i + 1);
            if (key.getBytes().length == 2) {
                value = (String) convert(key);
                if (value == null) {
                    value = "unknown";
                }
            } else {
                value = key;
            }
            buffer.append(value);
        }
        return buffer.toString();
    }

    public String getSpelling() {
        return this.getSelling(this.getResource());
    }

    /**
     * 转换为拼音
     *
     * @param str
     * @return
     */
    public static String trans2PinYin(String str) {
        return Trans2PinYin.getInstance().convertAll(str);
    }

}

最后的一些细节,比如Edittext监听什么的

 et_search.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {

            }

            @Override
            public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {

            }

            @Override
            public void afterTextChanged(Editable editable) {
                if (editable.length() > 0) {
                    tv_cancel.setVisibility(View.VISIBLE);
                } else {
                    tv_cancel.setVisibility(View.GONE);
                }
            }
        });

这些小细节大家等下自行下载我上传的源码看吧!

最后,这篇博客到这里也就结束了,字母导航的思路也借鉴了很多前人,自己摸索了一天多才摸索出来,感觉这个扩展性还可以强一点,无奈精力有限,篇幅也有限了,等我下次再继续研究,这么多,能看到这里也是不容易,我写的也不容易,给我点个赞吧!!!

我们最后看一下最终的效果

这里写图片描述

源码下载:正在上传

各位小伙伴来我的群里一起玩耍一下吧:555974449

作者:qq_26787115 发表于2016/9/11 20:51:53 原文链接
阅读:254 评论:1 查看评论

AT命令集详解

$
0
0

1.AT的历史与应用
 
  1.1 AT的历史
AT命令集是由拨号调制解调器(MODEM)的发明者贺氏公司(Hayes)为了控制Modem发明的控制协议.AT是Attention的缩写,协议本身采用文本.每个命令均以AT打头,因此得名.这段历史参见http://en.wikipedia.org/wiki/Hayes_command_set
 
随着网络升级为宽带,速度很低拨号MODEM基本已经退出一般使用市场.我最近一次看见使用拨号MODEM的地方是深圳市的网络报税系统.必要拨号到税务局的服务器才能使用。也就在这个很小的市场才留到一点空间。其余一般都用上ADSL的modem了。
贺氏公司象很多发明伟大的产品的公司一样,在发明了划时代的MODEM产品后,没有进一步升级技术。现在已经于1999年破产消失了,类似的例子有发明浏览器的Netscape,第一个成为网络操作系统的Novell公司,现在都已经边缘化了。
关于Hayes的破产,还能找到一个旧闻http://news.sina.com.cn/richtalk/news/tech/9901/010704.html
但是有意思,http://www.hayes.com仍在销售产品,难到又活过来了?
 
但是AT命令保留下来了。主要的移动电话生产厂商诺基亚、爱立信、摩托罗拉和HP共同为GSM 研制了一整套AT指令,用于控制手机GSM模块。其中就包括对SMS的控制。AT指令在此基础上演化并被加入GSM 07.05标准以及现在的GSM07.07标准。
在随后的GPRS控制,3G模块,以及工业上常用的PDU,均采用AT命令集来控制,这样AT命令实际在这一些产品上成为事实的标准。
 
  1.2 AT的优点
 
命令简单易懂,并且采用标准串口来收发AT命令,这样对设备控制大大简化了,转换成简单串口编程了。
AT命令提供了一组标准的硬件接口--串口。这个简化的硬件设计.较新的电信网络模块,几乎都采用串口硬件接口。
AT命令功能较全,可以通过一组命令完成设备的控制,完成呼叫、短信、电话本、数据业务、传真.
    
1.3 AT命令与ppp协议的关系
 
在数据通讯的应用中,比如说无线拨号上网。除了AT命令,还会常听到另外一个网络协议ppp(Point to Point Protocol)。
 
在应用串口通讯的场合,我们可以从硬件上明确看到分为两大块。
 
DTE(Data Terminal Equipment)数据终端设备。通常是一个智能设备,如PC机,嵌入式主机等,用于发送AT命令和PPP命令,
还有用于链路通讯的DCE(Data Circuit Terminal )数据电路终端。用于与外界建立通讯的链路。
DTE与DCE之间用串口相连。比如PC机用串口接入拨号MODEM时,PC机是DTE,拨号MODEM是DCE.
 
AT和PPP的相同点都是由DTE发送给DCE的协议。不同点是AT只用于DTE来控制DCE。比如初始化设备,用于发送呼叫,发送短消息等,虽然AT有规范,但是大部分DTE产商都扩展了一些AT命令。
 
而PPP是用于数据通讯,是DTE与远程的接入服务器(Access Server)进行通讯的协议。是属于网络通讯的数据链路层协议,DCE本身收到PPP包时,除了将其调制到物理层上发送到远端服务器外,本身并不处理PPP的内容。
 
2.AT的命令格式
  AT指令格式:AT指令都以”AT”开头,以<CR>(即\r,回车符)结束,模块运行后,串口默认的设置为:8位数据位、1位停止位、无奇偶校验位、硬件流控制(CTS/RTS).
  注意为了发送AT命令,最后还要加上<LF> (即\n,换行符)这是串口终端要求.
  有一些命令后面可以加额外信息来.如电话号码
 
  每个AT命令执行后,通常DCE都给状态值,用于判断命令执行的结果.
 
  AT返回状态包括三种情况 OK,ERROR,和命令相关的错误原因字符串.返回状态前后都有一个<CR>字符.
   如 <CR>OK<CR> 表示AT命令执行成功.
     <CR>ERROR<CR> 表示AT命令执行失败
     <CR>NO DIAL TONE<CR> 只出现在ATD命令返回状态中,表示没有拨号音,这类返回状态要查命令手册
 
   还有一些命令本身是要向DCE查询数据,数据返回时,一般是+打头命令.返回格式
    <CR>+命令:命令结果<CR>
如:AT+CMGR=8 (获取第8条信息)
  返回 +CMGR: "REC UNREAD","+8613508485560",,"01/07/16,15:37:28+32",Once more
  
 
3.DCE的状态切换与AT的命令拨号流程
 
  这两个协议都是DTE通过串口发往DCE。那DCE是如何区别是AT命令,如何区别PPP协议包?大部分DCE是采用分时段传送的,两个协议并不同时发送。但是可以通过AT命令两个专用命令来用切换是AT命令时段,还是PPP协议时段。
 
在发送AT命令时称为命令状态,在发送PPP包时或者语音通讯时称为数据状态。
 
在modem设备启动进,默认进入AT命令接收状态,用ATDn ;命令拨出电话号码n(语音拨号);ATDn 拨出电话号码n(数据拨号),两者区别在于前者有一个分号。用数据拨号拨通后,将进入PPP交互状态。当需要切回接收AT命令状态,DTE需要发送+++命令给DCE.让其保持在线的状态时,但接收是AT命令.如果此时需要切断链接,此时发送ATH挂断命令.
  注意发送+++需要前后各一秒的时间。否则会当成数据发送出去。
 
  ATO则是把在线命令状切换到数据接收状态。
 
 
 
 
一个DCE的拨号流程是
 
 3.1.初始化DCE的Modem设备
    主要DTE要配置好串口参数,并且向设备发送一些AT命令来进行初始化设置
 
  •     行软复位的需执行”ATZ\r”命令;
  •    禁止命令回显需执行”ATE0\r”命令;
  •    要使返回结果码为数字形式则要执行”ATV0\r”;
  •    需要设置S 寄存器的需执行”ATSn=X\r”等等。
 3.2 拨号连接
   AT拨号连接分语音拨号连接和数据拨好连接。语音拨号命令为”ATDn;\r”(注意带分号);数据拨号命令为”ATDn\r”(注意不带分号)。连接成功返回”\r\nCONNECTXXXX/RLP\r\n”,其中XXXX 表示连接速率。在这里我们只讨论数据拨号连接。要注意的是拨号连接需要一定的时间,编程时要根据实际情况进行适当的延时等待。
 
3.3 数据传输及处理
     在建立起连接后用户就可通过DCE进行数据发送、接收及数据处理操作。这时发送数据就是简单的写串口,收数据是读串口,即使数据中含有AT 命令字符串DCE也不会对其进行处理。此时进行PPP拨号处理流程了。
3.4  从数据状态切换至在线命令状态
   数据收发结束后,就要使DCE从数据状态切换至在线命令状态。向DCE发送换码序列命令”+++”,并且前后各有至少一秒的延迟(不向TC35 发数据),可使DCE从数据状态切换至在线命令状态,否则DEC会将”+++”当作数据发送出去。在离线命令状态时发送”ATO\r”可回到数据状态。
3.5  挂断连接
   挂断连接(即挂机)是向DCE发送”ATH\r”
 
 
4.常用AT命令
 
    不同产商的AT命令大同小异,但是还是有所区别,一般要看产品手册,如下列产商的
 
   这里罗列一些常见的AT命令
   4.1 基本操作
1.1 AT 
命令解释:检测Module与串口是否连通,能否接收AT命令;
命令格式:AT<CR>
命令返回:OK (与串口通信正常)(无返回,与串口通信未连通)
 
1.2 AT+CSQ
命令解释:检查网络信号强度和SIM卡情况
命令格式:AT+CSQ<CR>
命令返回:+CSQ: **,##
          其中**应在10到31之间,数值越大表明信号质量越好,##应为99。
          否则应检查天线或SIM卡是否正确安装
测试结果:AT+CSQ<CR>
          +CSQ: 31, 99
          信号强度值会有少许变化,用手遮住天线,信号强度值会下降(大致在26左右)。
1.3 ATZ 
命令解释:恢复原厂设置
命令格式:ATZ<CR>
命令返回:OK

1.4 AT+CGMR
命令解释:查询模块版本;
命令格式:AT+CGMR<CR>
命令返回: <revision >
         +CMEERROR <err>
测试结果:AT+CGMR<CR>
         R4A021      CXC1122528
          OK
解释:模块版本号为R4A021

1.5 AT+IPR
命令解释:修改串口1波特率;
命令格式:AT+IPR=<value ><CR>
命令返回: ERROR 
OK 
测试结果:AT+IPR=19200<CR>
OK
注意:串口波特率修改为19200后要把串口调试工具的波特率设为相应
波特率后模块才会有返回

1.6 AT&W 
命令解释:保存模块设置;
命令格式:AT&W<CR>
命令返回: OK
ERROR(保存不成功)
测试结果:AT&W <CR>
OK
4.2、通话操作
2.1ATD 
命令解释:拨打电话
命令格式:ATD**********;<CR>(****为电话号码)
命令返回:OK
NO DIAL TONE(没有拨号音)
NO CARRIER(无载波)
测试结果:a. ATD13510090403;<CR>
OK
呼叫成功;
b. ATD13510090403;<CR>
NO DIAL TONE
天线未接好,接触不良;
c. ATD13510090403<CR>
NO CARRIER
命令错误,缺{;};
2.2 RING
命令解释:有电话呼入
命令格式:
命令返回:无

2.3 ATA
命令解释:摘机
命令格式:ATA<CR>
命令返回:OK
测试结果:RING
RING
ATA<CR>
          OK
          接通电话;

2.4 ATH
命令解释:挂机
命令格式:ATH<CR>
命令返回:OK
测试结果:ATH<CR>
          OK
          电话挂断(通话过程中);

2.5 AT+CHUP
命令解释:挂机
命令格式:AT+CHUP<CR>
命令返回:OK
测试结果:RING
ATH<CR>
OK
电话挂断(尚未接通来电);

2.6AT+VTS
命令解释:拨打分机
命令格式:AT+VTS=“分机号码”<CR>
命令返回:OK
测试结果:
AT+VTS=“0”<CR>
OK

4.3、短信息操作

  短信操作步骤及相关命令:
(1) 设置短信格式——AT+CMGF
(2) 设置短信存储载体——AT+CPMS
(3) 设置短信接收提示方式——AT+CNMI
(4) 发送短信——AT+CMGS
(5) 显示短信——AT+CMGL

3.1 AT+CPMS
命令解释:选择短信存储载体

3.1.1命令格式:AT+CPMS=<mem1>[,<mem2>][,<mem3>]
设置短信存储载体
命令返回:+CPMS:<used1>,<total1>,<used2>,<total2>,<used3>,<total3>
          OK
          ERROR
测试结果:a. AT+CPMS=”SM”
           +CPMS: 8,15,8,15,1,40
           OK
           设置成功,并显示状态:SM(SIM卡)存储器总容量为15,当前存储量8;
           ME(模块)存储器总容量为40,当前存储量1;mem1定义为SM;
         b. AT+CPMS=”SM”,”SM”
           +CPMS: 8,15,8,15,1,40
           OK
           设置成功,并显示状态:SM存储器总容量为15,当前存储量8;
           ME存储器总容量为40,当前存储量1;mem1定义为SM;mem2
           定义为SM;
         c. AT+CPMS=”SM”,”SM”,”SM”
           +CPMS: 8,15,8,15,8,15
           OK
           设置成功,并显示状态:SM存储器总容量为15,当前存储量8;
           ME存储器总容量为40,当前存储量1;mem1定义为SM;mem2
           定义为SM;mem3定义为SM;
         d. AT+CPMS=”ME”,”SM”,”SM”
           +CPMS: 1,40,8,15,8,15
           OK
           设置成功,并显示状态:SM存储器总容量为15,当前存储量8;
           ME存储器总容量为40,当前存储量1;mem1定义为ME;mem2
           定义为SM;mem3定义为SM;
         e. AT+CPMS=”ME”,”SM”,”ME”
           +CPMS: 1,40,8,15,1,40
           OK
           设置成功,并显示状态:SM存储器总容量为15,当前存储量8;
           ME存储器总容量为40,当前存储量1;mem1定义为ME;mem2
           定义为SM;mem3定义为ME;
         f. AT+CPMS=”ME
           ERROR
           命令格式错误,缺少{”};

3.1.2命令格式:AT+CPMS?
          显示当前短信存储载体设置
命令返回:+CPMS:<mem1>,<used1>,<total1>,<mem1>,<used2>,<total2>,
                     <mem1>,<used3>,<total3>
          OK
          ERROR
测试结果:a. AT+CPMS?
            +CPMS: "SM",8,15,"SM",8,15,"ME",1,40
            OK
            当前短信存储载体设置为:mem1为SM,mem2为SM,mem3
            为ME;
          b. AT+CPMS!
             ERROR
             命令错误;

3.1.3命令格式:AT+CPMS=?
          显示本命令支持的参数
命令返回:+CPMS: (list of supported<mem1>s),(list of supported<mem2>s),
                    (list of supported<mem3>s)
          OK
          ERROR
测试结果:AT+CPMS=?
          +CPMS: ("ME","SM"),("ME","SM"),("ME","SM")
          OK

3.2 AT+CMGF
命令解释:设置短信格式
3.2.1命令格式:AT+CMGF=<mode>
命令返回:OK
          ERROR
               设置短信格式

3.2.2命令格式:AT+CMGF=?
命令返回:OK
          ERROR
          显示本命令支持的参数

3.2.3命令格式:AT+CMGF?
命令返回:OK
          ERROR
          显示当前短信格式
测试结果:AT+CMGF=?
+CMGF: (0,1)
OK
AT+CMGF?
+CMGF: 0
OK
AT+CMGF=1
OK
AT+CMGF?
+CMGF: 1
OK
    
3.3 AT+CMGS
命令解释:发送短信
命令格式:AT+CMGS=<da>[,<toda>]<CR>
          Text is entered<ctrl-z/ESC>
命令返回:+CMGS:<mr>[,<scts>]
          +CMS ERROR:<err>
          OK
          ERROR
测试结果:a. AT+CMGS=13510090403<CR>
          >ABCD1234.456<ctrl-z>
          +CMS ERROR:500
          命令错误;
        b. AT+CMGS="13510090403"<CR>
> IT IS TEST NOW<ctrl-z>
+CMGS: 235
OK

3.4 AT+CMGR
命令解释:读短信
命令格式:AT+CMGR=<indes>
命令返回:+CMGS:<stat>,[<alpha>],<length>]<CR><LF><pdu>
          +CMS ERROR:<err>
          OK
          ERROR
测试结果:a. AT+CMGR=5
          +CMS ERROR:500
          命令错误,5号短信位置为空;
        b. AT+CMGR=2
+CMGL: 2,"REC READ","+8613682326205","N?R","03/08/28 17:30:35+00"
998B76844F60002E518D5FCD5FCD5427+CMGS: 235
OK
读出2号短信;

3.5 AT+CMGW
命令解释:写短信,并保存到存储载体
命令格式:AT+CMGW=<length>[,<stat>]<CR>
命令返回:+CMGS:<index>
          +CMS ERROR:<err>
          OK
          ERROR
测试结果:AT+CMGW="13534139079"<CR>
> SHELLEY123456<ctrl-z>
+CMGW: 1
OK
把目标地址为13534139079的短信存入存储载体,且被分配的地址
为1号短信;

3.6 AT+CMGD
命令解释:删除短信
命令格式:AT+CMGD=<index>
命令返回:+CMS ERROR:<err>
          OK
          ERROR
测试结果:AT+CMGD=1
          OK
          1号短信被删除;

3.7 AT+CMGL
命令解释:显示短信清单
命令格式:AT+CMGL=<stat>
命令返回:+CMGL:<index1>,<stat>,<oa/da>,[<alpha>],[<scts>] [,<tooa/toda>,<length>]
<CR><LF><data>[<CR><LF>
测试结果:见总测试结果;

3.8 AT+CMSS
命令解释:发送存储载体中的短信
命令格式:AT+CMSS=<index>
命令返回:+CMSS:<mr>
+CMS ERROR:<err>
OK
ERROR
测试结果:AT+CMSS=2
+CMSS: 204
OK

3.9AT+CNMI
命令解释:新短信提示
3.9.1命令格式:AT+CNMI=[<mode>[,<mt>[,<bm>[,<ds>]]]]
命令返回:OK
  ERROR
测试结果:AT+CNMI=3,2
  OK

3.9.2命令格式:AT+CNMI?
命令返回:+CNMI:<mode>,<mt>,<bm>,<ds>
OK
ERROR
测试结果:AT+CNMI?
  +CNMI: 3,2,0,0
  OK

3.9.3命令格式:AT+CNMI=?
命令返回:+CNMI:(list of supported<mode>s), (list of supported<mt>s), (list of supported<bm>s),
(list of supported<ds>s) 
OK
ERROR
测试结果:AT+CNMI=3,2
OK


 4.4、语音部分:
 

  4.1 AT*E2EAMS
  命令解释:设定音频工作参数(修改语音通道)
   4.1.1  命令格式:AT*E2EAMS=<OP >,<NUM >,<VAL >
     命令返回:OK
         ERROR
     测试结果:<OP>为N在1-20之间,表示设置第N个参数
       AT*E2EAMS=9,2(把模块的语音MIC通道设定为手柄)
       OK
       AT*E2EAMS=10,2(把模块的语音SPK通道设定为手柄)
       OK
       <OP >为0表示设置所有参数
 AT*E2EAMS=0,2,1,2,0,0,2,5,9,2,2,0,1,0,0,0,1,1,0,0,1
 OK
      <OP >为255表示要保存设置
      AT*E2EAMS=255
 OK

4.5、GPS接口:

 5.1 AT*EENMEA
 命令解释:设定GPS数据使能
命令格式:AT*EENMEA=<val >
命令返回:OK
    ERROR
测试结果:
AT*EENMEA=0 (不接受串口2发来的NMEA数据)
OK
AT*EENMEA=2 (接受来自串口2的NMEA数据)
OK

5.2 AT*E2NMPR
命令解释:设定串口2发送GPS数据的波特率 
 5.2.1命令格式:AT*E2NMPR=<val >
命令返回:OK
          ERROR
测试结果:AT+CNMI=5 (设定串口2的波特率为19200)
OK
 
 
5.编程控制AT命令.
   5.1 Windows的串口编程

 

  1. #include < windows.h > 
  2.  
  3. HANDLE hCom = ((HANDLE)(0)); 
  4.  
  5. int main() 
  6.   DCB dcb; 
  7.   unsigned long int n = 0; 
  8.   char * str = "COM1"
  9.  
  10.   hCom = CreateFile( str, (GENERIC_READ | GENERIC_WRITE), 
  11.                      0, NULL, OPEN_EXISTING, 0, NULL ); 
  12.  
  13.   GetCommState ( hCom, (&(dcb)) ); 
  14.  
  15.   dcb.BaudRate = CBR_9600; 
  16.   dcb.ByteSize = 8; 
  17.   dcb.Parity = NOPARITY; 
  18.   dcb.StopBits = ONESTOPBIT; 
  19.  
  20.   SetCommState ( hCom, (&(dcb)) ); 
  21.  
  22.   WriteFile( hCom, "ATM2\r", strlen("ATM2\r"), (&(n)), 0 ); 
  23.   FlushFileBuffers( hCom ); 
  24.   Sleep(1000); 
  25.  
  26.   WriteFile( hCom, "ATH1\r", strlen("ATH1\r"), (&(n)), 0 ); 
  27.   FlushFileBuffers( hCom ); 
  28.   Sleep(1000); 
  29.  
  30.   WriteFile( hCom, "ATDT5551212;\r", strlen("ATDT5551212;\r"), (&(n)), 0 ); 
  31.   FlushFileBuffers( hCom ); 
  32.   Sleep(3000); 
  33.  
  34.   WriteFile( hCom, "ATH0\r", strlen("ATH0\r"), (&(n)), 0 ); 
  35.   FlushFileBuffers( hCom ); 
  36.   Sleep(1000); 
  37.  
  38.   WriteFile( hCom, "ATM0\r", strlen("ATM0\r"), (&(n)), 0 ); 
  39.   FlushFileBuffers( hCom ); 
  40.   Sleep(1000); 
  41.  
  42.   CloseHandle( hCom ); 
  43.  
  44.   return(0); 

 


作者:zqixiao_09 发表于2016/9/11 20:57:21 原文链接
阅读:83 评论:0 查看评论

自定义View之实用渐变色进度条

$
0
0

在网上看到一个进度条效果图,非常美观,如下:
这里写图片描述

进行效果分解:

1,渐变色,看起来颜色变化并不复杂,使用LinearGradient应该可以实现。
2,圆头,无非是画两个圆,外圆使用渐变色的颜色,内圆固定为白色。
3,灰底,还没有走到的进度部分为灰色。
4,进度值,使用文本来显示;
5,弧形的头部,考虑使用直线进行连接,或者使用曲线,例如贝塞尔曲线;

我首先初步实现了进度条的模样,发现样子有了,却不太美观。
反思了一下,我只是个写代码的,对于哪种比例比较美观,是没有清晰的认识的,所以,还是参考原图吧。

然后就进行了精细的测量:

将图像放大4倍,进行测量,然后获取到各部分的比例关系,具体过程就不细说了,说一下测量结果(按比例的):

视图总长300,其中前面留空5,进度长258,然后再留空5,显示文本占26,后面留空6;

高度分为4个:
外圆:10
字高:9
内圆:6
线粗:5
考虑上下各留空10,则视图的高度为30。

考虑到视图整体的效果,可以由用户来设置长度值与高度值,按比例取最小值来进行绘图。
首先计算出一个单位的实际像素数,各部分按比例来显示即可。

还有一个弧形的头部,是怎么实现的呢?
在放大之后,能看出来图形比较简单,看不出有弧度,那么,使用一小段直线连接就可以了。
估算这小段直线:线粗为2,呈30度角,长为8-10即可,连接直线与弧顶,起点在弧顶之左下方。
注意:在进度的起点时,不能画出。避免出现一个很突兀的小尾巴。在2%进度之后,才开始画。

在文字的绘制过程中,遇到一个小问题,就是文字不居中,略微偏下,上网查了下,原因是这样的:我们绘制文本时,使用的这个函数:canvas.drawText(“30%”, x, y, paint);
其中的参数 y 是指字符串baseline的的位置,不是文本的中心。通过计算可以调整为居中,如下:

        //计算坐标使文字居中
        FontMetrics fontMetrics = mPaint.getFontMetrics();  
        float  fontHeight = fontMetrics.bottom - fontMetrics.top;
        float baseY =  height/2 + fontHeight/2 - fontMetrics.bottom;

按比例来绘制之后,就确实是原来那个修长优雅的感觉了。
实际运行后,发现字体偏小,不太适合竖屏观看,调大了些。

另外对于参数,做了如下几个自定义属性:
前景色:开始颜色,结束颜色;
进度条未走到时的默认颜色,
字体颜色。

属性xml如下:

<?xml version="1.0" encoding="utf-8"?>
<resources>

    <attr name="startColor" format="color" />
    <attr name="endColor" format="color" />
    <attr name="backgroundColor" format="color" />
    <attr name="textColor" format="color" />

    <declare-styleable name="GoodProgressView">
        <attr name="startColor" />
        <attr name="endColor" />
        <attr name="backgroundColor" />
        <attr name="textColor" />   
    </declare-styleable>

</resources>

自定义View文件:

package com.customview.view;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.LinearGradient;
import android.graphics.Paint;
import android.graphics.Shader;
import android.graphics.Paint.Cap;
import android.graphics.Paint.FontMetrics;
import android.graphics.Paint.Style;
import android.util.AttributeSet;
import android.util.Log;
import android.view.View;
import com.customview.R;

public class GoodProgressView extends View
{
    private int[] mColors = { Color.RED, Color.MAGENTA};//进度条颜色(渐变色的2个点)
    private int backgroundColor = Color.GRAY;//进度条默认颜色
    private int textColor = Color.GRAY;//文本颜色

    private Paint mPaint;//画笔
    private int progressValue=0;//进度值
//  private RectF rect;//绘制范围

    public GoodProgressView(Context context, AttributeSet attrs)
    {       
        this(context, attrs, 0);
    }

    public GoodProgressView(Context context)
    {
        this(context, null);
    }

    // 获得我自定义的样式属性 
    public GoodProgressView(Context context, AttributeSet attrs, int defStyle)
    {
        super(context, attrs, defStyle);

        // 获得我们所定义的自定义样式属性 
        TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.GoodProgressView, defStyle, 0);
        int n = a.getIndexCount();
        for (int i = 0; i < n; i++)
        {
            int attr = a.getIndex(i);
            switch (attr)
            {
            case R.styleable.GoodProgressView_startColor:
                // 渐变色之起始颜色,默认设置为红色
                mColors[0] = a.getColor(attr, Color.RED);
                break;  
            case R.styleable.GoodProgressView_endColor:
                // 渐变色之结束颜色,默认设置为品红
                mColors[1] = a.getColor(attr, Color.MAGENTA);
                break;  
            case R.styleable.GoodProgressView_backgroundColor:
                // 进度条默认颜色,默认设置为灰色
                backgroundColor = a.getColor(attr, Color.GRAY);
                break;  
            case R.styleable.GoodProgressView_textColor:
                // 文字颜色,默认设置为灰色
                textColor = a.getColor(attr, Color.GRAY);
                break;  
            }
        }
        a.recycle();

        mPaint = new Paint();
        progressValue=0;
    }

    public void setProgressValue(int progressValue){

        if(progressValue>100){
            progressValue = 100;
        }
        this.progressValue = progressValue;
        Log.i("customView","log: progressValue="+progressValue);
    }

    public void setColors(int[] colors){
        mColors = colors;   
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec)
    {

        int width = 0;
        int height = 0;
        /**
         * 设置宽度
         */
        int specMode = MeasureSpec.getMode(widthMeasureSpec);
        int specSize = MeasureSpec.getSize(widthMeasureSpec);
        switch (specMode)
        {
        case MeasureSpec.EXACTLY:// 明确指定了
            width = specSize;
            break;
        case MeasureSpec.AT_MOST:// 一般为WARP_CONTENT
            width = getPaddingLeft() + getPaddingRight() ;
            break;
        }

        /**
         * 设置高度
         */
        specMode = MeasureSpec.getMode(heightMeasureSpec);
        specSize = MeasureSpec.getSize(heightMeasureSpec);
        switch (specMode)
        {
        case MeasureSpec.EXACTLY:// 明确指定了
            height = specSize;
            break;
        case MeasureSpec.AT_MOST:// 一般为WARP_CONTENT
            height = width/10;
            break;
        }

        Log.i("customView","log: w="+width+" h="+height);
        setMeasuredDimension(width, height);

    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);

        int mWidth = getMeasuredWidth();
        int mHeight = getMeasuredHeight();

        //按比例计算进度条各部分的值
        float unit = Math.min(((float)mWidth)/300, ((float)mHeight)/30);
        float lineWidth = 5*unit;//线粗
        float innerCircleDiameter = 6*unit;//内圆直径
        float outerCircleDiameter = 10*unit;//外圆直径
        float wordHeight = 12*unit;//字高//9*unit
//      float wordWidth = 26*unit;//字长
        float offsetLength = 5*unit;//留空
//      float width = 300*unit;//绘画区域的长度
        float height = 30*unit;//绘画区域的高度
        float progressWidth = 258*unit;//绘画区域的长度

        mPaint.setAntiAlias(true);
        mPaint.setStrokeWidth((float) lineWidth );
        mPaint.setStyle(Style.STROKE);
        mPaint.setStrokeCap(Cap.ROUND);

        mPaint.setColor(Color.TRANSPARENT);

        float offsetHeight=height/2;
        float offsetWidth=offsetLength;

        float section = ((float)progressValue) / 100;
        if(section>1)
            section=1;

        int count = mColors.length;
        int[] colors = new int[count];
        System.arraycopy(mColors, 0, colors, 0, count);         

        //底部灰色背景,指示进度条总长度
        mPaint.setShader(null);
        mPaint.setColor(backgroundColor);   
        canvas.drawLine(offsetWidth+section * progressWidth, offsetHeight, offsetWidth+progressWidth, offsetHeight, mPaint);

        //设置渐变色区域
        LinearGradient shader = new LinearGradient(0, 0, offsetWidth*2+progressWidth , 0, colors, null,
                Shader.TileMode.CLAMP);
        mPaint.setShader(shader);

        //画出渐变色进度条
        canvas.drawLine(offsetWidth, offsetHeight, offsetWidth+section*progressWidth, offsetHeight, mPaint);

        //渐变色外圆
        mPaint.setStrokeWidth(1);
        mPaint.setStyle(Paint.Style.FILL);
        canvas.drawCircle(offsetWidth+section * progressWidth, offsetHeight, outerCircleDiameter/2, mPaint);

        //绘制两条斜线,使外圆到进度条的连接更自然
        if(section*100>1.8){

            mPaint.setStrokeWidth(2*unit);
            canvas.drawLine(offsetWidth+section * progressWidth-6*unit, offsetHeight-(float)1.5*unit, 
                    offsetWidth+section * progressWidth-1*unit,offsetHeight-(float)3.8*unit, mPaint);

            canvas.drawLine(offsetWidth+section * progressWidth-6*unit, offsetHeight+(float)1.5*unit, 
                    offsetWidth+section * progressWidth-1*unit,offsetHeight+(float)3.8*unit, mPaint);
        }

        //白色内圆
        mPaint.setShader(null);
        mPaint.setColor(Color.WHITE);
        canvas.drawCircle(offsetWidth+section * progressWidth, offsetHeight, innerCircleDiameter/2, mPaint);//白色内圆


        //绘制文字--百分比
        mPaint.setStrokeWidth(2*unit);
        mPaint.setColor(textColor);
        mPaint.setTextSize(wordHeight);
        //计算坐标使文字居中
        FontMetrics fontMetrics = mPaint.getFontMetrics();  
        float  fontHeight = fontMetrics.bottom - fontMetrics.top;
        float baseY =  height/2 + fontHeight/2 - fontMetrics.bottom;
        canvas.drawText(""+progressValue+"%", progressWidth+2*offsetWidth, baseY, mPaint);//略微偏下,baseline

    }

}

主xml:

放了两个进度条,一个使用默认值,一个设置了进度条默认颜色与字体颜色:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:custom="http://schemas.android.com/apk/res/com.customview"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <com.customview.view.GoodProgressView
        android:id="@+id/good_progress_view1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:padding="10dp"               
        />   

    <com.customview.view.GoodProgressView
        android:id="@+id/good_progress_view2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_centerInParent="true" 
        custom:backgroundColor="#ffcccccc"
        custom:textColor="#ff000000"
        android:padding="10dp"               
        />   

</RelativeLayout>

Activity文件:

一个使用默认渐变色效果,一个的渐变色使用随机颜色,这样每次运行效果不同,比较有趣一些,另外我们也可以从随机效果中找到比较好的颜色组合。进度的变化,是使用了一个定时器来推进。

package com.customview;

import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.view.WindowManager;
import java.util.Random;
import java.util.Timer;
import java.util.TimerTask;
import com.customview.view.GoodProgressView;
import android.app.Activity;
import android.graphics.Color;

public class MainActivity extends Activity
{

    GoodProgressView good_progress_view1;
    GoodProgressView good_progress_view2;

    int progressValue=0;    

    @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN);//去掉信息栏

        setContentView(R.layout.activity_main);
        good_progress_view1 = (GoodProgressView)findViewById(R.id.good_progress_view1);
        good_progress_view2 = (GoodProgressView)findViewById(R.id.good_progress_view2);

        //第一个进度条使用默认进度颜色,第二个指定颜色(随机生成)
        good_progress_view2.setColors(randomColors());

        timer.schedule(task, 1000, 1000); // 1s后执行task,经过1s再次执行          
    }

    Handler handler = new Handler() {  
        public void handleMessage(Message msg) {  
            if (msg.what == 1) {  
                Log.i("log","handler : progressValue="+progressValue);

                //通知view,进度值有变化
                good_progress_view1.setProgressValue(progressValue*2);
                good_progress_view1.postInvalidate();

                good_progress_view2.setProgressValue(progressValue);
                good_progress_view2.postInvalidate();

                progressValue+=1;
                if(progressValue>100){
                    timer.cancel();
                }
            }  
            super.handleMessage(msg);              
        };  
    };  

    private int[] randomColors() {
        int[] colors=new int[2];

        Random random = new Random();
        int r,g,b;
        for(int i=0;i<2;i++){
            r=random.nextInt(256);
            g=random.nextInt(256);
            b=random.nextInt(256);
            colors[i]=Color.argb(255, r, g, b);
            Log.i("customView","log: colors["+i+"]="+Integer.toHexString(colors[i]));
        }

        return colors;
    }

    Timer timer = new Timer();  
    TimerTask task = new TimerTask() {  

        @Override  
        public void run() {  
            // 需要做的事:发送消息  
            Message message = new Message();  
            message.what = 1;  
            handler.sendMessage(message);  
        }  
    };  

}

最终效果如下:

竖屏时:
这里写图片描述

横屏时:
这里写图片描述

完整demo在如下地址:

http://download.csdn.net/detail/lintax/9627855

作者:lintax 发表于2016/9/11 20:58:03 原文链接
阅读:90 评论:0 查看评论

Fragment详解

$
0
0

Fragment

关于生命周期的图就不贴了,看着闹心,直接看方法解释吧

Fragment生命周期方法含义:

  • public void onAttach(Context context)

    • onAttach方法会在Fragment于窗口关联后立刻调用。从该方法开始,就可以通过Fragment.getActivity方法获取与Fragment关联的窗口对象,但因为Fragment的控件未初始化,所以不能够操作控件。
  • public void onCreate(Bundle savedInstanceState)

    • 在调用完onAttach执行完之后立刻调用onCreate方法,可以在Bundle对象中获取一些在Activity中传过来的数据。通常会在该方法中读取保存的状态,获取或初始化一些数据。在该方法中不要进行耗时操作,不然窗口不会显示。
  • public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState)

    • 该方法是Fragment很重要的一个生命周期方法,因为会在该方法中创建在Fragment显示的View,其中inflater是用来装载布局文件的,container是<fragment>标签的父标签对应对象,savedInstanceState参数可以获取Fragment保存的状态,如果未保存那么就为null。
  • public void onViewCreated(View view,Bundle savedInstanceState)

    • Android在创建完Fragment中的View对象之后,会立刻回调该方法。其种view参数就是onCreateView中返回的view,而bundle对象用于一般用途。
  • public void onActivityCreated(Bundle savedInstanceState)

    • 在Activity的onCreate方法执行完之后,Android系统会立刻调用该方法,表示窗口已经初始化完成,从这一个时候开始,就可以在Fragment中使用getActivity().findViewById(Id);来操控Activity中的view了。
  • public void onStart()

    • 这个没啥可讲的,但有一个细节需要知道,当系统调用该方法的时候,fragment已经显示在ui上,但还不能进行互动,因为onResume方法还没执行完。
  • public void onResume()

    • 该方法为fragment从创建到显示Android系统调用的最后一个生命周期方法,调用完该方法时候,fragment就可以与用户互动了。
  • public void onPause()

    • fragment由活跃状态变成非活跃状态执行的第一个回调方法,通常可以在这个方法中保存一些需要临时暂停的工作。如保存音乐播放进度,然后在onResume中恢复音乐播放进度。
  • public void onStop()

    • 当onStop返回的时候,fragment将从屏幕上消失。
  • public void onDestoryView()

    • 该方法的调用意味着在 onCreateView 中创建的视图都将被移除。
  • public void onDestroy()

    • Android在Fragment不再使用时会调用该方法,要注意的是~这时Fragment还和Activity藕断丝连!并且可以获得Fragment对象,但无法对获得的Fragment进行任何操作(呵~呵呵~我已经不听你的了)。
  • public void onDetach()

    • 为Fragment生命周期中的最后一个方法,当该方法执行完后,Fragment与Activity不再有关联(分手!我们分手!!(╯‵□′)╯︵┻━┻)。

Fragment比Activity多了几个额外的生命周期回调方法:

  • onAttach(Activity):当Fragment和Activity发生关联时使用
  • onCreateView(LayoutInflater, ViewGroup, Bundle):创建该Fragment的视图
  • onActivityCreate(Bundle):当Activity的onCreate方法返回时调用
  • onDestoryView():与onCreateView相对应,当该Fragment的视图被移除时调用
  • onDetach():与onAttach相对应,当Fragment与Activity关联被取消时调用

注意:除了onCreateView,其他的所有方法如果你重写了,必须调用父类对于该方法的实现

Fragment与Activity之间的交互

  • Fragment与Activity之间的交互可以通过Fragment.setArguments(Bundle args)以及Fragment.getArguments()来实现。

Fragment状态的持久化。

由于Activity会经常性的发生配置变化,所以依附它的Fragment就有需要将其状态保存起来问题。下面有两个常用的方法去将Fragment的状态持久化。

  • 方法一:
    • 可以通过protected void onSaveInstanceState(Bundle outState),protected void onRestoreInstanceState(Bundle savedInstanceState) 状态保存和恢复的方法将状态持久化。
  • 方法二(更方便,让Android自动帮我们保存Fragment状态):

    • 我们只需要将Fragment在Activity中作为一个变量整个保存,只要保存了Fragment,那么Fragment的状态就得到保存了,所以呢.....
      • FragmentManager.putFragment(Bundle bundle, String key, Fragment fragment) 是在Activity中保存Fragment的方法。
      • FragmentManager.getFragment(Bundle bundle, String key) 是在Activity中获取所保存的Frament的方法。
    • 很显然,key就传入Fragment的id,fragment就是你要保存状态的fragment,但,我们注意到上面的两个方法,第一个参数都是Bundle,这就意味着FragmentManager是通过Bundle去保存Fragment的。但是,这个方法仅仅能够保存Fragment中的控件状态,比如说EditText中用户已经输入的文字(注意!在这里,控件需要设置一个id,否则Android将不会为我们保存控件的状态),而Fragment中需要持久化的变量依然会丢失,但依然有解决办法,就是利用方法一!
    • 下面给出状态持久化的事例代码:

           /** Activity中的代码 **/
           FragmentB fragmentB;
      
          @Override
          protected void onCreate(@Nullable Bundle savedInstanceState) {
              super.onCreate(savedInstanceState);
              setContentView(R.layout.fragment_activity);
              if( savedInstanceState != null ){
                  fragmentB = (FragmentB) getSupportFragmentManager().getFragment(savedInstanceState,"fragmentB");
              }
              init();
          }
      
          @Override
          protected void onSaveInstanceState(Bundle outState) {
              if( fragmentB != null ){
                  getSupportFragmentManager().putFragment(outState,"fragmentB",fragmentB);
              }
      
              super.onSaveInstanceState(outState);
          }
      
          /** Fragment中保存变量的代码 **/
      
          @Nullable
          @Override
          public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
              AppLog.e("onCreateView");
              if ( null != savedInstanceState ){
                  String savedString = savedInstanceState.getString("string");
                  //得到保存下来的string
              }
              View root = inflater.inflate(R.layout.fragment_a,null);
              return root;
          }
      
          @Override
          public void onSaveInstanceState(Bundle outState) {
              outState.putString("string","anAngryAnt");
              super.onSaveInstanceState(outState);
          }
      
      

静态的使用Fragment

  1. 继承Fragment,重写onCreateView决定Fragment的布局
  2. 在Activity中声明此Fragment,就和普通的View一样

Fragment常用的API

  • android.support.v4.app.Fragment 主要用于定义Fragment
  • android.support.v4.app.FragmentManager 主要用于在Activity中操作Fragment,可以使用FragmentManager.findFragmenById,FragmentManager.findFragmentByTag等方法去找到一个Fragment
  • android.support.v4.app.FragmentTransaction 保证一些列Fragment操作的原子性,熟悉事务这个词
  • 主要的操作都是FragmentTransaction的方法(一般我们为了向下兼容,都使用support.v4包里面的Fragment)

    getFragmentManager() // Fragment若使用的是support.v4包中的,那就使用getSupportFragmentManager代替

  • 主要的操作都是FragmentTransaction的方法

    FragmentTransaction transaction = fm.benginTransatcion();//开启一个事务
    transaction.add() 
    //往Activity中添加一个Fragment

    transaction.remove() 
    //从Activity中移除一个Fragment,如果被移除的Fragment没有添加到回退栈(回退栈后面会详细说),这个Fragment实例将会被销毁。

    transaction.replace()
    //使用另一个Fragment替换当前的,实际上就是remove()然后add()的合体~

    transaction.hide()
    //隐藏当前的Fragment,仅仅是设为不可见,并不会销毁

    transaction.show()
    //显示之前隐藏的Fragment

    detach()
    //当fragment被加入到回退栈的时候,该方法与*remove()*的作用是相同的,
    //反之,该方法只是将fragment从视图中移除,
    //之后仍然可以通过*attach()*方法重新使用fragment,
    //而调用了*remove()*方法之后,
    //不仅将Fragment从视图中移除,fragment还将不再可用。

    attach()
    //重建view视图,附加到UI上并显示。

    transatcion.commit()
    //提交一个事务

管理Fragment回退栈

  • 跟踪回退栈状态

    • 我们通过实现OnBackStackChangedListener接口来实现回退栈状态跟踪,具体如下
    public class XXX implements FragmentManager.OnBackStackChangedListener 
    
    /** 实现接口所要实现的方法 **/
    
    @Override
    public void onBackStackChanged() {
        //do whatevery you want
    }
    
    /** 设置回退栈监听接口 **/
    getSupportFragmentManager().addOnBackStackChangedListener(this);
    
    
    
  • 管理回退栈

    • FragmentTransaction.addToBackStack(String) --将一个刚刚添加的Fragment加入到回退栈中
    • getSupportFragmentManager().getBackStackEntryCount() -获取回退栈中实体数量
    • getSupportFragmentManager().popBackStack(String name, int flags) -根据name立刻弹出栈顶的fragment
    • getSupportFragmentManager().popBackStack(int id, int flags) -根据id立刻弹出栈顶的fragment

作者:shangzhongjia 发表于2016/9/11 21:05:24 原文链接
阅读:92 评论:0 查看评论

Solr6.0与Jetty、Tomcat在Win环境下搭建/部署

$
0
0

摘要: Solr6的新特性包括增强的edismax,对SQL更好的支持——并行SQL、JDBC驱动、更多的SQL语法支持等,并且在Solr6发布以后,Solr5还在持续更新,对于想尝鲜Solr6的用户来说,与之前版本有什么不同,让我们一起来探究一下。

Solr6用默认的Jetty启动

  1. 需要的软件支持

  2. Solr自带一个Jetty环境,可以很方便的运行Solr。
    直接到解压缩的solr/bin目录运行solr start即可。
    solr start
    我的环境竟然是java1.7,查看一下
    java version
    怎么跟实际不符呢?原来,我的java1.8是直接安装的,它会将自己的运行文件复制一份放在C:\ProgramData\Oracle\Java\javapath(ProgramData是一个隐藏文件夹,需要设置后显示出来),但是我之前设置的JAVA_HOME没有改,将环境变量设置为java1.8后,再次启动。
    solr restart
    看到这样的信息,就可以了。
    solr UI

  3. 访问http://localhost:8983/solr 可以看到solr的图形化界面,但是我们的sore还是空的,需要手动创建。首先在 .\solr-6.0.0\server\solr目录下新建文件夹core0,把 .\solr-6.0.0\server\solr\configsets\basic_configs下的所有文件复制进来。
    在管理界面,点击No cores available选项,在弹出的窗口刚才新建的文件夹的名字。
    Add core
    这样,最简单的Solr就搭建完成了。
    Solr core UI
  4. 要想停止运行的话,在命令窗口运行solr stop
    solr stop

Solr6部署在Jetty9环境下

  1. 需要的软件支持

    • JDK1.8以上
    • Solr6的安装包(solr-6.0.0.zip 大约140M)
    • Jetty9.3.10(至少Jetty9.3.8以上,apache-tomcat-7.0.68-windows-x86.zip 大约11M)
  2. 在之前版本的Solr安装包中,存在solr.war文件,但是Solr6已经没有这个war包了,它已经被解压到了.\solr-6.0.0\server\solr-webapp文件夹下,将该文件夹下内容复制到.\jetty-9.3.10\webapps下,此时该目录应该为webapp,将其改为solr。
    webapps

  3. 日志处理:将Solr安装包中.\solr-6.0.0\server\lib\ext内的5个jar包复制到.\jetty-9.3.10\webapps\solr\WEB-INF\lib下。将.\solr-6.0.0\server\resources下的log4j.properties文件复制到.\jetty-9.3.10\webapps\solr\WEB-INF\classes中,这里的classes目录需要自己新建。log4j.properties文件中有一行log4j.appender.file.File=${solr.log}/solr.log指定log文件的存放路径,可以指定到特定的目录。
  4. 配置solr_home:在磁盘任意位置新建目录,取名solr_home,把.\solr-6.0.0\server\solr下的整个solr文件夹复制到solr_home,编辑.\jetty-9.3.10\webapps\solr\WEB-INF下的web.xml文件。
  5. 将web.xml文件注释去掉,<env-entry-value>中填刚才新建的solr_home路径
    <env-entry>
       <env-entry-name>solr/home</env-entry-name>
       <env-entry-value>E:\Tools\solr_home</env-entry-value>
       <env-entry-type>java.lang.String</env-entry-type>
    </env-entry>
  1. 这个solr_home里面的内容是复制.\solr-6.0.0\server\solr\下的内容,然后在该目录下新建文件夹core0,把 .\solr-6.0.0\server\solr\configsets\basic_configs\下的所有文件复制进来。
    这里写图片描述

  2. 启动:在jetty的安装目录,运行java -jar start.jar
    java -jar start.jar

  3. 访问http://localhost:8080/solr,可以看到solr管理界面,但是我们的sore还是空的,需要手动创建。在管理界面,点击No cores available选项,在弹出的窗口刚才新建的文件夹的名字。
    Add core
    这样,最简单的Solr就搭建完成了。
    solr UI

Solr6部署在Tomcat8环境下

  1. 需要的软件支持
    • JDK1.8以上
    • Solr6的安装包(solr-6.0.0.zip 大约140M)
    • Tomcat8(至少tomcat-8.0以上,apache-tomcat-8.5.5-windows-x86.zip 约10M)
  2. 在之前版本的Solr安装包中,存在solr.war文件,但是Solr6已经没有这个war包了,它已经被解压到了.\solr-6.0.0\server\solr-webapp文件夹下,将该文件夹下内容复制到.\apache-tomcat-8.5.5\webapps下,此时该目录应该为webapp,将其改为solr。
    solr file
  3. 日志处理:将Solr安装包中.\solr-6.0.0\server\lib\ext内的5个jar包复制到.\apache-tomcat-8.5.5\webapps\solr\WEB-INF\lib下。将.\solr-6.0.0\server\resources下的log4j.properties文件复制到.\apache-tomcat-8.5.5\webapps\solr\WEB-INF\classes中,这里的classes目录需要自己新建。log4j.properties文件中有一行log4j.appender.file.File=${solr.log}/solr.log指定log文件的存放路径,可以指定到特定的目录。
  4. 配置solr_home:在磁盘任意位置新建目录,取名solr_home,把.\solr-6.0.0\server\solr下的整个solr文件夹复制到solr_home,编辑.\apache-tomcat-8.5.5\webapps\solr\WEB-INF下的web.xml文件。
  5. 将web.xml文件注释去掉,<env-entry-value>中填刚才新建的solr_home路径
    <env-entry>
       <env-entry-name>solr/home</env-entry-name>
       <env-entry-value>E:\Tools\solr_home</env-entry-value>
       <env-entry-type>java.lang.String</env-entry-type>
    </env-entry>
  1. 这个solr_home里面的内容是复制.\solr-6.0.0\server\solr\下的内容,然后在该目录下新建文件夹core0,把 .\solr-6.0.0\server\solr\configsets\basic_configs\下的所有文件复制进来。
    这里写图片描述
  2. 运行的话,直接双击startup.bat
    startup.bat
  3. 访问http://localhost:8080/solr,可以看到solr管理界面,但是我们的sore还是空的,需要手动创建。在管理界面,点击No cores available选项,在弹出的窗口刚才新建的文件夹的名字。
    Add core
    这样,最简单的Solr就搭建完成了。
    solr UI
作者:jiangchao858 发表于2016/9/11 21:06:28 原文链接
阅读:86 评论:0 查看评论
Viewing all 5930 articles
Browse latest View live


<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>