当前位置:  编程技术>移动开发
本页文章导读:
    ▪XCode的一些调试技艺 控制台        XCode的一些调试技巧 控制台看了牛人的这篇文章,感觉真是很有用啊,受益匪浅  http://blog.csdn.net/kesalin/article/details/7222153 XCode 内置GDB,我们可以在命令行中使用 GDB 命令来调试我们的程序.........
    ▪ 将assets资料拷贝到SD卡中,或者拷贝到内存的data/./files/下        将assets文件拷贝到SD卡中,或者拷贝到内存的data/.../files/下 public class RootPathFunction extends CordovaPlugin { private static final String TAG = RootPathFunction.class.getSimpleName(); private String mActionName = "rootFilePat.........
    ▪ Fragment的容易demo       Fragment的简单demo package com.example.googleandroiddemo; // //import android.app.Activity; //import android.os.Bundle; //import android.support.v4.app.FragmentTransaction; //import android.support.v4.app.ListFragment; //import android.view.View; .........

[1]XCode的一些调试技艺 控制台
    来源: 互联网  发布时间: 2014-02-18
XCode的一些调试技巧 控制台

看了牛人的这篇文章,感觉真是很有用啊,受益匪浅  http://blog.csdn.net/kesalin/article/details/7222153

XCode 内置GDB,我们可以在命令行中使用 GDB 命令来调试我们的程序。下面将介绍一些常用的命令以及调试技巧。

po 命令:为 print object 的缩写,显示对象的文本描述(显示从对象的 description 消息获得的字符串信息)。

比如:

上图中,我使用 po 命令显示一个 NSDictionary 的内容。注意在左侧我们可以看到 dict 的一些信息:3 key/value pairs,显示该 dict 包含的数据量,而展开的信息显示 isa 层次体系(即class 和 metaclass结构关系)。我们可以右击左侧的 dict,选中“Print Description of "dict"”,则可以在控制台输出 dict 的详细信息:

[cpp] view plaincopyprint?
  • Printing description of dict:  
  • <CFBasicHash 0x1001149e0 [0x7fff7e27ff40]>{type = immutable dict, count = 3,  
  • entries =>  
  •     0 : <CFString 0x100002458 [0x7fff7e27ff40]>{contents = "first"} = <CFString 0x100002438 [0x7fff7e27ff40]>{contents = "one"}  
  •     1 : <CFString 0x100002498 [0x7fff7e27ff40]>{contents = "second"} = <CFString 0x100002478 [0x7fff7e27ff40]>{contents = "two"}  
  •     2 : <CFString 0x1000024d8 [0x7fff7e27ff40]>{contents = "third"} = <CFString 0x1000024b8 [0x7fff7e27ff40]>{contents = "three"}  
  • }  
  • (gdb)   

  • print 命令:有点类似于格式化输出,可以输出对象的不同信息:

    如:

    [cpp] view plaincopyprint?
  • (gdb) print (char *)[[dict description] cStringUsingEncoding:4]  
  • $1 = 0x1001159c0 "{\n    first = one;\n    second = two;\n    third = three;\n}"  
  • (gdb) print (int)[dict retainCount]  
  • $2 = 1  
  • (gdb)   
  • 注:4是 NSUTF8StringEncoding 的值。

    info 命令:我们可以查看内存地址所在信息

    比如 "info symbol 内存地址" 可以获取内存地址所在的 symbol 相关信息:

    [cpp] view plaincopyprint?
  • (gdb) info symbol 0x00000001000017f7  
  • main + 343 in section LC_SEGMENT.__TEXT.__text of /Users/LuoZhaohui/Library/Developer/Xcode/DerivedData/RunTimeSystem-anzdlhiwvlbizpfureuvenvmatnp/Build/Products/Debug/RunTimeSystem  
  • 比如 "info line *内存地址" 可以获取内存地址所在的代码行相关信息:

    [cpp] view plaincopyprint?
  • (gdb) info line *0x00000001000017f7  
  • Line 62 of "/Users/LuoZhaohui/Documents/Study/RunTimeSystem/RunTimeSystem/main.m" starts at address 0x1000017f7 <main+343> and ends at 0x10000180a <main+362>.  
  • show 命令:显示 GDB 相关的信息。如:show version 显示GDB版本信息

    [cpp] view plaincopyprint?
  • (gdb) show version  
  • GNU gdb 6.3.50-20050815 (Apple version gdb-1708) (Mon Aug  8 20:32:45 UTC 2011)  
  • Copyright 2004 Free Software Foundation, Inc.  
  • GDB is free software, covered by the GNU General Public License, and you are  
  • welcome to change it and/or distribute copies of it under certain conditions.  
  • Type "show copying" to see the conditions.  
  • There is absolutely no warranty for GDB.  Type "show warranty" for details.  
  • This GDB was configured as "x86_64-apple-darwin".  

  • help 命令:如果忘记某条命令的语法了,可以使用 help 命令名 来获取帮助信息。如:help info 显示 info 命令的用法。
    [cpp] view plaincopyprint?
  • (gdb) help info  
  • Generic command for showing things about the program being debugged.  
  •   
  • List of info subcommands:  
  •   
  • info address -- Describe where symbol SYM is stored  
  • info all-registers -- List of all registers and their contents  
  • info args -- Argument variables of current stack frame  
  • info auxv -- Display the inferior's auxiliary vector  
  • info breakpoints -- Status of user-settable breakpoints  
  • info catch -- Exceptions that can be caught in the current stack frame  
  • info checkpoints -- Help  
  • info classes -- All Objective-C classes  
  • ......  
  •   
  • Type "help info" followed by info subcommand name for full documentation.  
  • Command name abbreviations are allowed if unambiguous.  
  • (gdb)   
  • 在系统抛出异常处设置断点

    有时候我们的程序不知道跑到哪个地方就 crash 了,而 crash 又很难重现。保守的做法是在系统抛出异常之前设置断点,具体来说是在 objc_exception_throw处设置断点。设置步骤为:首先在 XCode 按 CMD + 6,进入断点管理窗口;然后点击右下方的 +,增加新的 Symbolic Breakpoint,在 Symbol 一栏输入:objc_exception_throw,然后点击 done,完成。 这样在 Debug 模式下,如果程序即将抛出异常,就能在抛出异常处中断了。比如在前面的代码中,我让 [firstObjctcrashTest]; 抛出异常。在 objc_exception_throw 处设置断点之后,程序就能在该代码处中断了,我们从而知道代码在什么地方出问题了。



        
    [2] 将assets资料拷贝到SD卡中,或者拷贝到内存的data/./files/下
        来源: 互联网  发布时间: 2014-02-18
    将assets文件拷贝到SD卡中,或者拷贝到内存的data/.../files/下
    public class RootPathFunction extends CordovaPlugin {
    private static final String TAG = RootPathFunction.class.getSimpleName();
    private String mActionName = "rootFilePath";
    private Context context;
    private String filePath = "/www/";
    private String path;

    @Override
    public void initialize(CordovaInterface cordova, CordovaWebView webView) {
    super.initialize(cordova, webView);
    context = cordova.getActivity();
    Log.e(TAG, "initialize");
    File root = Environment.getExternalStorageDirectory();// getDataDirectory();
    File rootRes = new File(root.getPath() + filePath);
    path = rootRes.getPath();
    //copyAssets("www", path);
    copyAssets2("www");
    }

    @Override
    public boolean execute(String action, JSONArray args,
    CallbackContext callbackContext) throws JSONException {
    Log.e(TAG, "execute action="/blog_article/action/index.html",args=" + args.toString());
    if (action.equals(mActionName)) {
    callbackContext.success(path);
    return true;
    } else {
    callbackContext.error("rootFilePath is failed!");
    return false;
    }
    }

    private void copyAssets(String assetDir, String dir) {
    String[] files;
    try {
    files = context.getResources().getAssets().list(assetDir);
    } catch (IOException e1) {
    return;
    }
    File mWorkingPath = new File(dir);
    if (!mWorkingPath.exists()) {
    mWorkingPath.mkdirs();
    }
    for (int i = 0; i < files.length; i++) {
    try {
    String fileName = files[i];
    if (isFolder(fileName)) {
    if (0 == assetDir.length()) {
    copyAssets(fileName, dir + File.separator + fileName
    + File.separator);
    } else {
    copyAssets(assetDir + File.separator + fileName, dir
    + File.separator + fileName + File.separator);
    }
    continue;
    }
    File outFile = new File(mWorkingPath, fileName);
    if (outFile.exists())
    outFile.delete();
    InputStream in = null;
    if (0 != assetDir.length())
    in = context.getAssets().open(
    assetDir + File.separator + fileName);
    else
    in = context.getAssets().open(fileName);
    OutputStream out = new FileOutputStream(outFile);
    byte[] buf = new byte[1024];
    int len;
    while ((len = in.read(buf)) > 0) {
    out.write(buf, 0, len);
    }
    in.close();
    out.close();
    } catch (FileNotFoundException e) {
    e.printStackTrace();
    } catch (IOException e) {
    e.printStackTrace();
    }
    }
    }

    String[] suffixs = { ".png", ".jpg", ".css", ".js", ".html", ".htm",
    ".jsp", ".apx", ".txt", ".LICENSE" };

    private boolean isFolder(String fileName) {
    for (int i = 0; i < suffixs.length; i++) {
    if (fileName.contains(suffixs[i])) {
    return false;
    }
    }
    return true;
    }

    private void copyAssets2(String assetDir) {
    String[] files;
    try {
    files = context.getResources().getAssets().list(assetDir);
    } catch (IOException e1) {
    return;
    }
    for (int i = 0; i < files.length; i++) {
    try {
    String fileName = files[i];
    if (isFolder(fileName)) {
    continue;
    }
    FileOutputStream fileOutputStream = context.openFileOutput(fileName, context.MODE_WORLD_WRITEABLE);
    InputStream in = null;
    if (0 != assetDir.length())
    in = context.getAssets().open(
    assetDir + File.separator + fileName);
    else
    in = context.getAssets().open(fileName);
    OutputStream out = fileOutputStream;
    byte[] buf = new byte[1024];
    int len;
    while ((len = in.read(buf)) > 0) {
    out.write(buf, 0, len);
    }
    in.close();
    out.close();
    } catch (FileNotFoundException e) {
    e.printStackTrace();
    } catch (IOException e) {
    e.printStackTrace();
    }
    }
    }
    }

        
    [3] Fragment的容易demo
        来源: 互联网  发布时间: 2014-02-18
    Fragment的简单demo
    package com.example.googleandroiddemo;
    //
    //import android.app.Activity;
    //import android.os.Bundle;
    //import android.support.v4.app.FragmentTransaction;
    //import android.support.v4.app.ListFragment;
    //import android.view.View;
    //import android.widget.ArrayAdapter;
    //import android.widget.ListView;
    //
    //public class MainActivity extends Activity {
    //	@Override
    //	protected void onCreate(Bundle savedInstanceState) {
    //		super.onCreate(savedInstanceState);
    //
    //		setContentView(R.layout.fragment_layout);
    //	}
    //	
    //	
    //	public static class TitlesFragment extends ListFragment {
    //		public TitlesFragment() {
    //			super();
    //			// TODO Auto-generated constructor stub
    //		}
    //		
    //	    public static TitlesFragment newInstance(int index) {
    //	    	TitlesFragment f = new TitlesFragment();
    //
    //	        // Supply index input as an argument.
    ////	        Bundle args = new Bundle();
    ////	        args.putInt("index", index);
    ////	        f.setArguments(args);
    //
    //	        return f;
    //	    }
    //
    //		boolean mDualPane;
    //		int mCurCheckPosition = 0;
    //		String str[] = { "321321", "312312", "312312", "321321312","eqweqwewqeqw","eqwewqeqwwe","eqweqweqwerewre","r4r4r4t","eqwewqe" };
    //		@Override
    //		public void onActivityCreated(Bundle savedInstanceState) {
    //			super.onActivityCreated(savedInstanceState);
    //
    //			// Populate list with our static array of titles.
    //			setListAdapter(new ArrayAdapter<String>(getActivity(),
    //					android.R.layout.simple_list_item_activated_1,
    //					str));
    //
    //			// Check to see if we have a frame in which to embed the details
    //			// fragment directly in the containing UI.
    //			View detailsFrame = getActivity().findViewById(R.id.details);
    //			mDualPane = detailsFrame != null
    //					&& detailsFrame.getVisibility() == View.VISIBLE;
    //
    //			if (savedInstanceState != null) {
    //				// Restore last state for checked position.
    //				mCurCheckPosition = savedInstanceState.getInt("curChoice", 0);
    //			}
    //
    //			if (mDualPane) {
    //				// In dual-pane mode, the list view highlights the selected item.
    //				getListView().setChoiceMode(ListView.CHOICE_MODE_SINGLE);
    //				// Make sure our UI is in the correct state.
    //				showDetails(mCurCheckPosition);
    //			}
    //		}
    //
    //		@Override
    //		public void onSaveInstanceState(Bundle outState) {
    //			super.onSaveInstanceState(outState);
    //			outState.putInt("curChoice", mCurCheckPosition);
    //		}
    //
    //		@Override
    //		public void onListItemClick(ListView l, View v, int position, long id) {
    //			showDetails(position);
    //		}
    //
    //		/**
    //		 * Helper function to show the details of a selected item, either by
    //		 * displaying a fragment in-place in the current UI, or starting a whole new
    //		 * activity in which it is displayed.
    //		 */
    //		void showDetails(int index) {
    //			mCurCheckPosition = index;
    //
    //			if (mDualPane) {
    //				// We can display everything in-place with fragments, so update
    //				// the list to highlight the selected item and show the data.
    //				getListView().setItemChecked(index, true);
    //
    //				// Check what fragment is currently shown, replace if needed.
    //				DetailsFragment details = (DetailsFragment) getFragmentManager()
    //						.findFragmentById(R.id.details);
    //				if (details == null || details.getShownIndex() != index) {
    //					// Make new fragment to show this selection.
    //					details = DetailsFragment.newInstance(index);
    //
    //					// Execute a transaction, replacing any existing fragment
    //					// with this one inside the frame.
    //					FragmentTransaction ft = getFragmentManager()
    //							.beginTransaction();
    //					ft.replace(R.id.details, details);
    //					ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
    //					ft.commit();
    //				}
    //
    //			} else {
    //				// Otherwise we need to launch a new activity to display
    //				// the dialog fragment with selected text.
    //				// Intent intent = new Intent();
    //				// intent.setClass(getActivity(), DetailsActivity.class);
    //				// intent.putExtra("index", index);
    //				// startActivity(intent);
    //			}
    //		}
    //	}
    //}
    
    
    import android.annotation.SuppressLint;
    import android.annotation.TargetApi;
    import android.app.Activity;
    import android.app.AlertDialog;
    import android.app.Fragment;
    import android.app.FragmentTransaction;
    import android.app.ListFragment;
    import android.os.Bundle;
    //import android.support.v4.app.Fragment;
    //import android.support.v4.app.FragmentTransaction;
    //import android.support.v4.app.ListFragment;
    import android.util.TypedValue;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.ArrayAdapter;
    import android.widget.ListView;
    import android.widget.ScrollView;
    import android.widget.TextView;
    
    
    public class MainActivity extends Activity {
    
        public static String[] array = { "text1,", "text2", "text3", "text4",
                "text5,", "text6", "text7", "text8" };
    
        /** Called when the activity is first created. */
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState); 
            setContentView(R.layout.fragment_layout);
        }
    
            
        public static class TitlesFragment extends ListFragment {
    
            boolean mDualPane;
            int mCurCheckPosition = 0;
            
            @Override
            public void onCreate(Bundle savedInstanceState) {
                // TODO Auto-generated method stub
                super.onCreate(savedInstanceState);
                System.out.println("Fragment-->onCreate");
            }
            
            @Override
            public View onCreateView(LayoutInflater inflater, ViewGroup container,
                    Bundle savedInstanceState) {
                // TODO Auto-generated method stub
                System.out.println("Fragment-->onCreateView");
                return super.onCreateView(inflater, container, savedInstanceState);
            }
            
            @Override
            public void onPause() {
                // TODO Auto-generated method stub
                super.onPause();
                System.out.println("Fragment-->onPause");
            }
            
            
            @Override
            public void onStop() {
                // TODO Auto-generated method stub
                super.onStop();
                
                System.out.println("Fragment-->onStop");
            }
            
            @Override
            public void onAttach(Activity activity) {
                // TODO Auto-generated method stub
                super.onAttach(activity);
                System.out.println("Fragment-->onAttach");
            }
            
            @Override
            public void onStart() {
                // TODO Auto-generated method stub
                super.onStart();
                System.out.println("Fragment-->onStart");
            }
            
            @Override
            public void onResume() {
                // TODO Auto-generated method stub
                super.onResume();
                System.out.println("Fragment-->onResume");
            }
            
            @Override
            public void onDestroy() {
                // TODO Auto-generated method stub
                super.onDestroy();
                System.out.println("Fragment-->onDestroy");
            }
            
            
    
            @Override
            public void onActivityCreated(Bundle savedInstanceState) {
                // TODO Auto-generated method stub
                super.onActivityCreated(savedInstanceState);
                System.out.println("Fragment-->onActivityCreted");
                setListAdapter(new ArrayAdapter<String>(getActivity(),
                        android.R.layout.simple_list_item_1, array));
    
                View detailsFrame = getActivity().findViewById(R.id.details);
    
                mDualPane = detailsFrame != null
                        && detailsFrame.getVisibility() == View.VISIBLE;
    
                if (savedInstanceState != null) {
                    mCurCheckPosition = savedInstanceState.getInt("curChoice", 0); //从保存的状态中取出数据
                }
    
                if (mDualPane) {
                    getListView().setChoiceMode(ListView.CHOICE_MODE_SINGLE);
    
                    showDetails(mCurCheckPosition);
                }
            }
    
            @Override
            public void onSaveInstanceState(Bundle outState) {
                // TODO Auto-generated method stub
                super.onSaveInstanceState(outState);
    
                outState.putInt("curChoice", mCurCheckPosition);//保存当前的下标
            }
    
            @Override
            public void onListItemClick(ListView l, View v, int position, long id) {
                // TODO Auto-generated method stub
                super.onListItemClick(l, v, position, id);
                showDetails(position);
            }
    
            void showDetails(int index) {
                mCurCheckPosition = index; 
                if (mDualPane) {
                    getListView().setItemChecked(index, true);
                    DetailsFragment details = (DetailsFragment) getFragmentManager()
                            .findFragmentById(R.id.details); 
                    if (details == null || details.getShownIndex() != index) {
                        details = DetailsFragment.newInstance(mCurCheckPosition); 
    
                        //得到一个fragment 事务(类似sqlite的操作)
                        FragmentTransaction ft = getFragmentManager()
                                .beginTransaction();
                        ft.replace(R.id.details, details);//将得到的fragment 替换当前的viewGroup内容,add则不替换会依次累加
                        ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);//设置动画效果
                        ft.commit();//提交
                    }
                } else {
                    new AlertDialog.Builder(getActivity()).setTitle(
                            android.R.string.dialog_alert_title).setMessage(
                            array[index]).setPositiveButton(android.R.string.ok,
                            null).show();
                }
            }
        }
    
        /**
         * 作为界面的一部分,为fragment 提供一个layout
         * @author terry
         *
         */
        public static class DetailsFragment extends Fragment {
    
            public static DetailsFragment newInstance(int index) { 
                DetailsFragment details = new DetailsFragment();
                Bundle args = new Bundle();
                args.putInt("index", index);
                details.setArguments(args);
                return details;
            }
    
            public int getShownIndex() {
                return getArguments().getInt("index", 0);
            }
    
            @Override
            public View onCreateView(LayoutInflater inflater, ViewGroup container,
                    Bundle savedInstanceState) {
                // TODO Auto-generated method stub
                if (container == null)
                    return null;
    
                ScrollView scroller = new ScrollView(getActivity());
                TextView text = new TextView(getActivity());
    
                int padding = (int) TypedValue.applyDimension(
                        TypedValue.COMPLEX_UNIT_DIP, 4, getActivity()
                                .getResources().getDisplayMetrics());
                text.setPadding(padding, padding, padding, padding);
                scroller.addView(text);
    
                text.setText(array[getShownIndex()]);
                return scroller;
            }
        }
    }
    


    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="horizontal" >
    
       <fragment  android:id="@+id/titles" android:layout_weight="1"
           android:layout_width="0px" android:layout_height="match_parent"
           />
       
       <FrameLayout android:id="@+id/details" android:layout_weight="1" android:layout_width="0px" android:layout_height="match_parent"
           android:background="?android:attr/detailsElementBackground"
           ></FrameLayout>
    </LinearLayout>

        
    最新技术文章:
    ▪Android开发之登录验证实例教程
    ▪Android开发之注册登录方法示例
    ▪Android获取手机SIM卡运营商信息的方法
    ▪Android实现将已发送的短信写入短信数据库的...
    ▪Android发送短信功能代码
    ▪Android根据电话号码获得联系人头像实例代码
    ▪Android中GPS定位的用法实例
    ▪Android实现退出时关闭所有Activity的方法
    ▪Android实现文件的分割和组装
    ▪Android录音应用实例教程
    ▪Android双击返回键退出程序的实现方法
    ▪Android实现侦听电池状态显示、电量及充电动...
    ▪Android获取当前已连接的wifi信号强度的方法
    ▪Android实现动态显示或隐藏密码输入框的内容
    ▪根据USER-AGENT判断手机类型并跳转到相应的app...
    ▪Android Touch事件分发过程详解
    ▪Android中实现为TextView添加多个可点击的文本
    ▪Android程序设计之AIDL实例详解
    ▪Android显式启动与隐式启动Activity的区别介绍
    ▪Android按钮单击事件的四种常用写法总结
    ▪Android消息处理机制Looper和Handler详解
    ▪Android实现Back功能代码片段总结
    ▪Android实用的代码片段 常用代码总结
    ▪Android实现弹出键盘的方法
    ▪Android中通过view方式获取当前Activity的屏幕截...
    ▪Android提高之自定义Menu(TabMenu)实现方法
    ▪Android提高之多方向抽屉实现方法
    ▪Android提高之MediaPlayer播放网络音频的实现方法...
    ▪Android提高之MediaPlayer播放网络视频的实现方法...
    ▪Android提高之手游转电视游戏的模拟操控
     


    站内导航:


    特别声明:169IT网站部分信息来自互联网,如果侵犯您的权利,请及时告知,本站将立即删除!

    ©2012-2021,,E-mail:www_#163.com(请将#改为@)

    浙ICP备11055608号-3