在CSDN中,经常有人问如何打开Excel数据库文件。本文通过一个简单的例子,实现读取Excel数据文件。首先,创建一个Web应用程序项目,在Web页中添加一个DataGrid控件、一个文件控件和一个按钮控件。<INPUT id="File1" type="file" name="File1" runat="server"><asp:Button id="Button1" runat="server" Text="Button"></asp:Button><asp:DataGrid id="DataGrid1" runat="server"></asp:DataGrid>在代码视图中首先导入OleDb命名空间:using System.Data.OleDb; 在按钮的单击事件中输入如下代码:string strPath="c://test//" + DateTime.Now.ToString("yyyyMMddhhmmss") + ".xls";File1.PostedFile.SaveAs(strPath);string mystring="Provider = Microsoft.Jet.OLEDB.4.0 ; Data Source = '"+ strPath +"';Extended Properties=Excel 8.0";OleDbConnection cnnxls = new OleDbConnection (mystring);OleDbDataAdapter myDa =new OleDbDataAdapter("select * from [Sheet1$]",cnnxls);DataSet myDs =new DataSet();myDa.Fill(myDs); DataGrid1.DataSource=myDs.Tables[0];DataGrid1.DataBind();其中C:/test对ASPNET用户要有读写的权限. from:http://www.cnblogs.com/ranzige/p/3707316.html
View Details生成EXCEL文件是经常需要用到的功能,我们利用一些开源库可以很容易实现这个功能。 方法一:利用excellibrary,http://code.google.com/p/excellibrary/ excellibrary是国人写的开源组件,很容易使用,可惜貌似还不支持.xlsx(Excel 2007),例子如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
//Create the data set and table DataSet ds = new DataSet("New_DataSet"); DataTable dt = new DataTable("New_DataTable"); //Set the locale for each ds.Locale = System.Threading.Thread.CurrentThread.CurrentCulture; dt.Locale = System.Threading.Thread.CurrentThread.CurrentCulture; //Open a DB connection (in this example with OleDB) OleDbConnection con = new OleDbConnection(dbConnectionString); con.Open(); //Create a query and fill the data table with the data from the DB string sql = "SELECT Whatever FROM MyDBTable;"; OleDbCommand cmd = new OleDbCommand(sql, con); OleDbDataAdapter adptr = new OleDbDataAdapter(); adptr.SelectCommand = cmd; adptr.Fill(dt); con.Close(); //Add the table to the data set ds.Tables.Add(dt); //Here's the easy part. Create the Excel worksheet from the data set ExcelLibrary.DataSetHelper.CreateWorkbook("MyExcelFile.xls", ds); |
例子二:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 |
//create new xls file string file = "C:\\newdoc.xls"; Workbook workbook = new Workbook(); Worksheet worksheet = new Worksheet("First Sheet"); worksheet.Cells[0, 1] = new Cell((short)1); worksheet.Cells[2, 0] = new Cell(9999999); worksheet.Cells[3, 3] = new Cell((decimal)3.45); worksheet.Cells[2, 2] = new Cell("Text string"); worksheet.Cells[2, 4] = new Cell("Second string"); worksheet.Cells[4, 0] = new Cell(32764.5, "#,##0.00"); worksheet.Cells[5, 1] = new Cell(DateTime.Now, @"YYYY\-MM\-DD"); worksheet.Cells.ColumnWidth[0, 1] = 3000; workbook.Worksheets.Add(worksheet); workbook.Save(file); // open xls file Workbook book = Workbook.Load(file); Worksheet sheet = book.Worksheets[0]; // traverse cells foreach (Pair<Pair<int, int>, Cell> cell in sheet.Cells) { dgvCells[cell.Left.Right, cell.Left.Left].Value = cell.Right.Value; } // traverse rows by Index for (int rowIndex = sheet.Cells.FirstRowIndex; rowIndex <= sheet.Cells.LastRowIndex; rowIndex++) { Row row = sheet.Cells.GetRow(rowIndex); for (int colIndex = row.FirstColIndex; colIndex <= row.LastColIndex; colIndex++) { Cell cell = row.GetCell(colIndex); } } |
方法二:利用EPPlus,http://epplus.codeplex.com/ EPPlus是一个使用Open Office XML(xlsx)文件格式,能读写Excel 2007/2010 文件的开源组件。 例子如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
var file = @"Sample.xlsx"; if (File.Exists(file)) File.Delete(file); using (var excel = new ExcelPackage(new FileInfo(file))) { var ws = excel.Workbook.Worksheets.Add("Sheet1"); ws.Cells[1, 1].Value = "Date"; ws.Cells[1, 2].Value = "Price"; ws.Cells[1, 3].Value = "Volume"; var random = new Random(); for (int i = 0; i < 10; i++) { ws.Cells[i + 2, 1].Value = DateTime.Today.AddDays(i); ws.Cells[i + 2, 2].Value = random.NextDouble() * 1e3; ws.Cells[i + 2, 3].Value = random.Next() / 1e3; } ws.Cells[2, 1, 11, 1].Style.Numberformat.Format = "dd/MM/yyyy"; ws.Cells[2, 2, 11, 2].Style.Numberformat.Format = "#,##0.000000"; ws.Cells[2, 3, 11, 3].Style.Numberformat.Format = "#,##0"; ws.Column(1).AutoFit(); ws.Column(2).AutoFit(); ws.Column(3).AutoFit(); excel.Save(); } |
例子二:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 |
using OfficeOpenXml; //指定Templete文档Text.xlsx FileInfo newFile = new FileInfo("D:" + @"\Test.xlsx"); //开启 using (ExcelPackage pck = new ExcelPackage(newFile)) { try { //设定ExcelWorkBook ExcelWorkbook workBook = pck.Workbook; if (workBook != null) { if (workBook.Worksheets.Count > 0) { //复制Temp这个Sheet同时命名为《清单》 ExcelWorksheet currentWorksheet = workBook.Worksheets.Copy("Temp", "清单"); //可以设定保护Sheet的密码 //currentWorksheet.Protection.SetPassword("1234"); int StartRow = 4; for (int i = 0; i < tDS.Tables[0].Rows.Count; i++) { //Cells[RowIndex,CellIndex] currentWorksheet.Cells[StartRow + i, 1].Value = Convert.ToString(tDS.Tables[0].Rows[i][0]); currentWorksheet.Cells[StartRow + i, 2].Value = Convert.ToString(tDS.Tables[0].Rows[i][1]); currentWorksheet.Cells[StartRow + i, 3].Value = Convert.ToString(tDS.Tables[0].Rows[i][2]); currentWorksheet.Cells[StartRow + i, 4].Value = Convert.ToString(tDS.Tables[0].Rows[i][3]); currentWorksheet.Cells[StartRow + i, 5].Value = Convert.ToString(tDS.Tables[0].Rows[i][4]); currentWorksheet.Cells[StartRow + i, 6].Value = Convert.ToString(tDS.Tables[0].Rows[i][5]); currentWorksheet.Cells[StartRow + i, 7].Value = Convert.ToString(tDS.Tables[0].Rows[i][6]); currentWorksheet.Cells[StartRow + i, 8].Value = Convert.ToString(tDS.Tables[0].Rows[i][7]); currentWorksheet.Cells[StartRow + i, 9].Value = Convert.ToString(tDS.Tables[0].Rows[i][8]); currentWorksheet.Cells[StartRow + i, 10].Value = Convert.ToString(tDS.Tables[0].Rows[i][9]); currentWorksheet.Cells[StartRow + i, 11].Value = Convert.ToString(tDS.Tables[0].Rows[i][10]); currentWorksheet.Cells[StartRow + i, 12].Value = Convert.ToString(tDS.Tables[0].Rows[i][11]); currentWorksheet.Cells[StartRow + i, 13].Value = Convert.ToString(tDS.Tables[0].Rows[i][12]); } //将Temp 这个Sheet删除 workBook.Worksheets.Delete("Temp"); } } //存至Text4.xlsx pck.SaveAs(new FileInfo("H:" + @"\Test4.xlsx")); } catch (Exception e) { oLogger.Fatal(e.ToString()); } } |
方法三:NPOI http://npoi.codeplex.com/ NPOI无需Office COM组件且不依赖Office,使用NPOI能够帮助开发者在没有安装微软Office的情况下读写Office 97-2003的文件,支持的文件格式包括xls, doc, ppt等。NPOI是构建在POI 3.x版本之上的,它可以在没有安装Office的情况下对Word/Excel文档进行读写操作。 被人称为操作EXCEL的终极方案,例子如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
//引用 using NPOI.HSSF.UserModel; using NPOI.HPSF; using NPOI.POIFS.FileSystem; using NPOI.SS.UserModel; //将WorkBook指到我们原本设计好的Templete Book1.xls using (IWorkbook wb = new HSSFWorkbook(new FileStream("D:/Book1.xls", FileMode.Open))) { try { //设定要使用的Sheet为第0个Sheet ISheet TempSheet = wb.GetSheetAt(0); int StartRow = 4; //tDS为Query回来的资料 for (int i = 0; i < tDS.Tables[0].Rows.Count; i++) { //第一个Row要用Create的 TempSheet.CreateRow(StartRow + i).CreateCell(0).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][0])); //第二个Row之后直接用Get的 TempSheet.GetRow(StartRow + i).CreateCell(1).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][1])); TempSheet.GetRow(StartRow + i).CreateCell(2).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][2])); TempSheet.GetRow(StartRow + i).CreateCell(3).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][3])); TempSheet.GetRow(StartRow + i).CreateCell(4).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][4])); TempSheet.GetRow(StartRow + i).CreateCell(5).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][5])); TempSheet.GetRow(StartRow + i).CreateCell(6).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][6])); TempSheet.GetRow(StartRow + i).CreateCell(7).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][7])); TempSheet.GetRow(StartRow + i).CreateCell(8).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][8])); TempSheet.GetRow(StartRow + i).CreateCell(9).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][9])); TempSheet.GetRow(StartRow + i).CreateCell(10).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][10])); TempSheet.GetRow(StartRow + i).CreateCell(11).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][11])); TempSheet.GetRow(StartRow + i).CreateCell(12).SetCellValue(Convert.ToString(tDS.Tables[0].Rows[i][12])); } //将文档写到指定位置 using (FileStream file = new FileStream("H:/Test_NPOI4.xls", FileMode.Create)) { wb.Write(file); file.Close(); file.Dispose(); } } catch (Exception e) { string a = e.ToString(); } } |
from:http://www.cnblogs.com/kingboy2008/p/3711168.html
View Details关于C# C#是达成微软公共语言运行库(CLR)的少数语言中的一种。达成CLR的语言可以受益于其带来的特性,如跨语言集成、异常处理、安全性增强、部件组合的简易模型以及调试和分析服务。作为现代的CLR语言,C#是应用最为广泛的,其应用场景针对Windows桌面、移动手机以及服务器环境等复杂、专业的开发项目。 C#是种面向对象的强类型语言。C#在编译和运行时都有的强类型检查,使在大多数典型的编程错误能够被尽早地发现,而且位置定位相当精准。相比于那些不拘泥类型,在违规操作很久后才报出可追踪到莫名其妙错误的语言,这可以为程序员节省很多时间。然而,许多程序员有意或无意地抛弃了这个检测的有点,这导致本文中讨论的一些问题。 关于本文 本文描述了10个 C# 程序员常犯的错误,或应该避免的陷阱。 尽管本文讨论的大多数错误是针对 C# 的,有些错误与其他以 CLR 为目标的语言,或者用到了 Framework Class Library (FCL) 的语言也相关。 常见错误 #1: 把引用当做值来用,或者反过来 C++ 和其他很多语言的程序员,习惯了给变量赋值的时候,要么赋单纯的值,要么是现有对象的引用。然而,在C# 中,是值还是引用,是由写这个对象的程序员决定的,而不是实例化对象并赋值的程序员决定的。这往往会坑到 C# 的新手程序员。 如果你不知道你正在使用的对象是否是值类型或引用类型,你可能会遇到一些惊喜。例如:
1 2 3 4 5 6 7 8 9 10 11 |
Point point1 = new Point(20, 30); Point point2 = point1; point2.X = 50; Console.WriteLine(point1.X); // 20 (does this surprise you?) Console.WriteLine(point2.X); // 50 Pen pen1 = new Pen(Color.Black); Pen pen2 = pen1; pen2.Color = Color.Blue; Console.WriteLine(pen1.Color); // Blue (or does this surprise you?) Console.WriteLine(pen2.Color); // Blue |
如你所见,尽管Point和Pen对象的创建方式相同,但是当一个新的X的坐标值被分配到point2时, point1的值保持不变 。而当一个新的color值被分配到pen2,pen1也随之改变。因此,我们可以推断point1和point2每个都包含自己的Point对象的副本,而pen1和pen2引用了同一个Pen对象 。如果没有这个测试,我们怎么能够知道这个原理? 一种办法是去看一下对象是如何定义的(在Visual Studio中,你可以把光标放在对象的名字上,并按下F12键)
1 2 |
public struct Point { … } // defines a “value” type public class Pen { … } // defines a “reference” type |
如上所示,在C#中,struct关键字是用来定义一个值类型,而class关键字是用来定义引用类型的。 对于那些有C++编程背景人来说,如果被C++和C#之间某些类似的关键字搞混,可能会对以上这种行为感到很吃惊。 如果你想要依赖的行为会因值类型和引用类型而异,举例来说,如果你想把一个对象作为参数传给一个方法,并在这个方法中修改这个对象的状态。你一定要确保你在处理正确的类型对象。 常见的错误#2:误会未初始化变量的默认值 在C#中,值得类型不能为空。根据定义,值的类型值,甚至初始化变量的值类型必须有一个值。这就是所谓的该类型的默认值。这通常会导致以下,意想不到的结果时,检查一个变量是否未初始化:
1 2 3 4 5 6 |
class Program { static Point point1; static Pen pen1; static void Main(string[] args) { Console.WriteLine(pen1 == null); // True Console.WriteLine(point1 == null); // False (huh?) } } |
为什么不是【point 1】空?答案是,点是一个值类型,和默认值点(0,0)一样,没有空值。未能认识到这是一个非常简单和常见的错误,在C#中 很多(但是不是全部)值类型有一个【IsEmpty】属性,你可以看看它等于默认值:
1 |
Console.WriteLine(point1.IsEmpty); // True |
当你检查一个变量是否已经初始化,确保你知道值未初始化是变量的类型,将会在默认情况下,不为空值。 常见错误 #3: 使用不恰当或未指定的方法比较字符串 在C#中有很多方法来比较字符串。 虽然有不少程序员使用==操作符来比较字符串,但是这种方法实际上是最不推荐使用的。主要原因是由于这种方法没有在代码中显示的指定使用哪种类型去比较字符串。 相反,在C#中判断字符串是否相等最好使用Equals方法:
1 |
public bool Equals(string value); public bool Equals(string value, StringComparison comparisonType); |
第一个Equals方法(没有comparisonType这参数)和使用==操作符的结果是一样的,但好处是,它显式的指明了比较类型。它会按顺序逐字节的去比较字符串。在很多情况下,这正是你所期望的比较类型,尤其是当比较一些通过编程设置的字符串,像文件名,环境变量,属性等。在这些情况下,只要按顺序逐字节的比较就可以了。使用不带comparisonType参数的Equals方法进行比较的唯一一点不好的地方在于那些读你程序代码的人可能不知道你的比较类型是什么。 使用带comparisonType的Equals方法去比较字符串,不仅会使你的代码更清晰,还会使你去考虑清楚要用哪种类型去比较字符串。这种方法非常值得你去使用,因为尽管在英语中,按顺序进行的比较和按语言区域进行的比较之间并没有太多的区别,但是在其他的一些语种可能会有很大的不同。如果你忽略了这种可能性,无疑是为你自己在未来的道路上挖了很多“坑”。举例来说:
1 2 3 4 5 6 7 8 9 10 11 12 |
string s = "strasse"; // outputs False: Console.WriteLine(s == "stra&szlig;e"); Console.WriteLine(s.Equals("stra&szlig;e")); Console.WriteLine(s.Equals("stra&szlig;e", StringComparison.Ordinal)); Console.WriteLine(s.Equals("Stra&szlig;e", StringComparison.CurrentCulture)); Console.WriteLine(s.Equals("stra&szlig;e", StringComparison.OrdinalIgnoreCase)); // outputs True: Console.WriteLine(s.Equals("stra&szlig;e", StringComparison.CurrentCulture)); Console.WriteLine(s.Equals("Stra&szlig;e", StringComparison.CurrentCultureIgnoreCase)); |
最安全的实践是总是为Equals方法提供一个comparisonType的参数。 下面是一些基本的指导原则: 当比较用户输入的字符串或者将字符串比较结果展示给用户时,使用本地化的比较(CurrentCulture 或者CurrentCultureIgnoreCase)。 当用于程序设计的比较字符串时,使用原始的比较(Ordinal 或者 OrdinalIgnoreCase) InvariantCulture和InvariantCultureIgnoreCase一般并不使用,除非在受限的情境之下,因为原始的比较通常效率更高。如果与本地文化相关的比较是必不可少的,它应该被执行成基于当前的文化或者另一种特殊文化的比较。 此外,对Equals 方法来说,字符串也通常提供了Compare方法,可以提供字符串的相对顺序信息而不仅仅中测试是否相等。这个方法可以很好适用于<, <=, >和>= 运算符,对上述讨论同样适用。 常见误区 #4: 使用迭代式 (而不是声明式)的语句去操作集合 在C# 3.0中,LINQ的引入改变了我们以往对集合对象的查询和修改操作。从这以后,你应该用LINQ去操作集合,而不是通过迭代的方式。 一些C#的程序员甚至都不知道LINQ的存在,好在不知道的人正在逐步减少。但是还有些人误以为LINQ只用在数据库查询中,因为LINQ的关键字和SQL语句实在是太像了。 虽然数据库的查询操作是LINQ的一个非常典型的应用,但是它同样可以应用于各种可枚举的集合对象。(如:任何实现了IEnumerable接口的对象)。举例来说,如果你有一个Account类型的数组,不要写成下面这样:
1 2 3 4 |
decimal total = 0; foreach (Account account in myAccounts) { if (account.Status == "active") { total += account.Balance; } } |
你只要这样写:
1 2 3 |
decimal total = (from account in myAccounts where account.Status == "active" select account.Balance).Sum(); |
虽然这是一个很简单的例子,在有些情况下,一个单一的LINQ语句可以轻易地替换掉你代码中一个迭代循环(或嵌套循环)里的几十条语句。更少的代码通常意味着产生Bug的机会也会更少地被引入。然而,记住,在性能方面可能要权衡一下。在性能很关键的场景,尤其是你的迭代代码能够对你的集合进行假设时,LINQ做不到,所以一定要在这两种方法之间比较一下性能。 #5常见错误:在LINQ语句之中没有考虑底层对象 对于处理抽象操纵集合任务,LINQ无疑是庞大的。无论他们是在内存的对象,数据库表,或者XML文档。在如此一个完美世界之中,你不需要知道底层对象。然而在这儿的错误是假设我们生活在一个完美世界之中。事实上,相同的LINQ语句能返回不同的结果,当在精确的相同数据上执行时,如果该数据碰巧在一个不同的格式之中。 例如,请考虑下面的语句: 1 decimal total=(from accout in myaccouts 2 where accout.status==‘active" 3 select accout .Balance).sum(); 想象一下,该对象之一的账号会发生什么。状态等于“有效的”(注意大写A)? 好吧,如果myaccout是Dbset的对象。(默认设置了不同区分大小写的配置),where表达式仍会匹配该元素。然而,如果myaccout是在内存阵列之中,那么它将不匹配,因此将产生不同的总的结果。 等一会,在我们之前讨论过的字符串比较中, 我们看见 == 操作符扮演的角色就是简单的比较. 所以,为什么在这个条件下, == 表现出的是另外的一个形式呢 ? 答案是,当在LINQ语句中的基础对象都引用到SQL表中的数据(如与在这个例子中,在实体框架为DbSet的对象的情况下),该语句被转换成一个T-SQL语句。然后遵循的T-SQL的规则,而不是C#的规则,所以在上述情况下的比较结束是不区分大小写的。 […]
View Detailspackage com.w3cnet.db; import android.content.Context; import android.content.ContentValues; import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteOpenHelper; import android.database.Cursor; public class SqliteHelper extends SQLiteOpenHelper{ private final static String DATABASE_NAME = "db_name"; private final static int DATABASE_VERSION = 1; private final static String TABLE_NAME = "mytable"; private final static String FIELD_ID = "ID"; private final static String FIELD_NAME = "NAME"; public SqliteHelper(Context context) { super(context, DATABASE_NAME, null, DATABASE_VERSION); } @Override public void onCreate(SQLiteDatabase db) { String sql = "Create table %s (%s integer primary key autoincrement,%s text);"; sql = String.format(sql, TABLE_NAME, FIELD_ID, FIELD_NAME); db.execSQL(sql); } @Override […]
View Details对于一个Android应用程序来说,是由四种关键构造块组织而成的,这四种构造块分别是:Activity、Intent Receiver、Service、Content Provider 但是,并不是每一个Android应用程序都需要这四种构造块,这不是必须的,某些时候,我们只需要这四种中的几种组合成我们的应用。 当我们明确了我们的应用需要哪些构造块后,我们就需要在AndroidManifest.xml中登记这些构造块的清单。这是一个XML配置文件,这个配置文件用于定义我们的应用程序的组件、组件的功能及必要条件等。这个配置文件是每个Android应用必需的。对于AndroidMainfest.xml的Schema,我们对四种构造块做一些说明: 1、Activity Activity是Android构造块中最基本的一种,在应用中,一个 activity通常就是一个单独的屏幕。每一个activity都被实现为一个独立的类,并且继承于Activity这个基类。这个activity类将会显示由几个Views控件组成的用户接口,并对事件做出响应。大部份的应用都会包含多个的屏幕。例如,一个短消息应用程序将会有一个屏幕用于显示联系人列表,第二个屏幕用于写短消息,同时还会有用于浏览旧短消息及进行系统设置的屏幕。每一个这样的屏幕,就是一个activity。从一个屏幕导航到另一个屏幕是很简单的。在一些应用中,一个屏幕甚至会返回值给前一个屏幕。 当一个新的屏幕打开后,前一个屏幕将会暂停,并保存在历史堆栈中。用户可以返回到历史堆栈中的前一个屏幕。当屏幕不再使用时,还可以从历史堆栈中删除。默认情况下,Android将会保留从主屏幕到每一个应用的运行屏幕。 Android使用了Intent这个特殊类,实现在屏幕与屏幕之间移动。 Intent类用于描述一个应用将会做什么事。在Intent的描述结构中,有两个最重要的部分:动作和动作对应的数据。典型的动作类型有:MAIN(activity的门户)、VIEW、PICK、EDIT等。而动作对应的数据则以URI的形式进行表示。例如:要查看一个人的联系方式,你需要创建一个动作类型为VIEW的intent,以及一个表示这个人的URI。 与之有关系的一个类叫IntentFilter。相对于intent是一个有效的做某事的请求,一个intent filter则用于描述一个activity(或者Intent Receiver)能够操作哪些intent。一个activity如果要显示一个人的联系方式时,需要声明一个IntentFilter,这个 IntentFilter要知道怎么去处理VIEW动作和表示一个人的URI。IntentFilter需要在AndroidManifest.xml中定义。 通过解析各种intent,从一个屏幕导航到另一个屏幕是很简单的。当向前导航时,activity将会调用 startActivity(Intent myIntent)方法。然后,系统会在所有安装的应用程序中定义的IntentFilter中查找,找到最匹配myIntent的Intent对应的 activity。新的activity接收到myIntent的通知后,开始运行。当startActivity方法被调用将触发解析myIntent 的动作,这个机制提供了两个关键好处: ◆Activities能够重复利用从其它组件中以Intent的形式产生的一个请求; ◆Activities可以在任何时候被一个具有相同IntentFilter的新的Activity取代。 2、Intent Receiver 当你希望你的应用能够对一个外部的事件(如当电话呼入时,或者数据网络可用时,或者到了晚上时)做出响应,你可以使用一个Intent Receiver。虽然Intent Receiver在感兴趣的事件发生时,会使用NotificationManager通知用户,但它并不能生成一个UI。Intent Receiver在AndroidManifest.xml中注册,但也可以在代码中使用 Context.registerReceiver()进行注册。当一个intent receiver被触发时,你的应用不必对请求调用intent receiver,系统会在需要的时候启动你的应用。各种应用还可以通过使用Context.broadcastIntent()将它们自己的 intent receiver广播给其它应用程序。 3、Service 一个Service是一段长生命周期的,没有用户界面的程序。比较好的一个例子就是一个正在从播放列表中播放歌曲的媒体播放器。在一个媒体播放器的应用中,应该会有多个activity,让使用者可以选择歌曲并播放歌曲。然而,音乐重放这个功能并没有对应的activity,因为使用者当然会认为在导航到其它屏幕时音乐应该还在播放的。在这个例子中,媒体播放器这个 activity会使用Context.startService()来启动一个service,从而可以在后台保持音乐的播放。同时,系统也将保持这个service一直执行,直到这个service运行结束。另外,我们还可以通过使用Context.bindService()方法,连接到一个service上(如果这个service还没有运行将启动它)。当连接到一个service之后,我们还可以service提供的接口与它进行通讯。拿媒体播放器这个例子来说,我们还可以进行暂停、重播等操作。 4、Content Provider 应用程序能够将它们的数据保存到文件中、SQL数据库中,甚至是任何有效的设备中。当你想将你的应用数据与其它的应用共享时,Content Provider将会很有用。一个Content Provider类实现了一组标准的方法,从而能够让其它的应用保存或读取此Content Provider处理的各种数据类型。 from:http://mobile.51cto.com/mobile-114018.htm
View Details1. Android是什么? Android 是Google开发的基于Linux平台的开源手机操作系统。它包括操作系统、用户界面和应用程序 —— 移动电话工作所需的全部软件,而且不存在任何以往阻碍移动产业创新的专有权障碍。谷歌与开放手机联盟合作开发了 Android,这个联盟由包括中国移动、摩托罗拉、高通、宏达和 T-Mobile 在内的 30 多家技术和无线应用的领军企业组成。 Android 作为谷歌企业战略的重要组成部分,将进一步推进"随时随地为每个人提供信息"这一企业目标的实现。 2. Android用什么语言开发的? Android的SDK(software development kit)是Java的,将来可能有其他语言版本。 SDK下载地址:http://code.google.com/android/download.html 3. Android模拟器是用什么开发的? Android的核心是Java虚拟机,为了高效,目前来看,google是不会支持其它语言的开发的。不过,android的模拟器是用qeum开发的,它的镜像文件分成4部分放在tools目录下,如果我们将qeum修改一下,说不定能玩一下它的linux系统。 4. 怎么进行Android开发? Android支持在模拟器上运行和调试应用软件,有兴趣的朋友可以下载他的SDK(software development kit)来了解android的界面;然后应该学习android的基本框架和应用程序的构成;最后就可以试着在sdk的API Demo的基础上开发自己的application了。 希望刚刚了解软件开发的朋友不要着急,一步一个脚印,一定会茁壮成长,开发优秀的application的。 5. 有哪些好的网络资源可供Android学习者用的呢? 首先,最好的最基本的学习资料无疑是SDK的文档了,也就是这个地方(http://code.google.com/intl/zh-CN/android/documentation.html)的介绍,它循序渐进的介绍了Android的各个方面。 其次,大家可能有对android文档不太理解的地方,或者自己的想法等等,完全可以通过下面的groups进行咨询和交流: ◆Android Beginner http://groups.google.com/group/android-beginners?lnk= ◆Developper Groups http://groups.google.com/group/android-developers ◆Android Internals http://groups.google.com/group/android-internals?lnk= ◆Android Porting http://groups.google.com/group/android-porting?lnk= 【编辑推荐】 Android创建和使用数据库详细指南 细看Google Android的开源姿态 分析称Android 2012年超越iPhone平台 from:http://mobile.51cto.com/android-114004.htm
View Details最后更新对应的版本:1.2.5.1 教程描述: 富文本编辑器的使用开发中,表单提交有多种场景,编辑器初始化有新增文章和编辑就文章两种场景,提交表单有普通提交也有ajax提交表单两种情景,此教程详细讲解这几种场景下如何保证后台正确拿到数据。 一、编辑器内容初始化(即往编辑器中设置富文本) 场景一:写新文章,编辑器中预置提示、问候等内容。 在editor_config.js文件中找到initialContent参数,设置其值为需要的提示或者问候语即可,如initialContent:’欢迎使用UEditor!’。 场景二:编辑旧文章,从数据库中取出富文本放置到编辑器中。 显然,编辑文章时需要从后台数据库中取出大段富文本,如果仍然采用场景一中的方式去设置初始值的话,必然会带来诸如引号匹配被截断等问题,因此需要采用另外一种方式去设置,如下代码所示: <script type="text/plain" id="editor"> //从数据库中取出文章内容打印到此处 </script> 复制代码 此处采用了script标签作为编辑器容器对象,并设置了其类型是纯文本,从而在避免了标签内部JS代码执行的同时解决了部分同学在使用传统的textarea标签作为容器所带来的一次额外转码问题,只要此处设置的内容不为空字符串,内容会覆盖配置文件的initialContent参数的值。 二、提交编辑器内容至后端 场景一:在编辑器所在的Form中存在提交按钮,提交动作由点击此按钮完成。 该场景适用于最普通的场合,没有太大问题需要注意,仅三点说明: 1) 默认情况下提交到后台的表单名称是 "editorValue",在editor_config.js中可以配置,参数名为textarea。 2) 可以在容器标签(即script标签)上设置name属性,以覆盖editor_config.js中的默认配置。实例代码如下,此处的 myContent将成为新的提交表单名称: <form action="" method="post"> <script type="text/plain" id="editor" name="myContent"></script> <input type="submit" name="submit" value="提交"> </form> 复制代码 3)后端接收程序可以通过如下几种方式来获取编辑器中的富文本内容。 //PHP获取: $_POST["myContent"] //JSP获取: request.getParameter("myContent"); //ASP获取: request("myContent"); //NET获取: context.Request.Form["myContent"]; 复制代码 场景二:编辑器所在的Form中不存在提交按钮,提交动作由外部事件触发。 该场景适用于站点前端交互较多的场合,需要注意的事项主要是在触发form提交动作之前执行编辑器内容同步操作。一般的代码模式如下所示: //满足提交条件时同步内容并提交,此处editor为编辑器实例 if(editor.hasContents()){ //此处以非空为例 editor.sync(); //同步内容 someForm.submit(); //提交Form } 复制代码 另外,如果是js代码动态去获取表单内容,可以直接调用editor.getContent()方法。 场景三:编辑器不在任何Form中,提交动作由外部事件触发。 该场景使用不多,但特殊时候可能需要。UEditor也提供了对应的处理方案,基本逻辑跟场景二一样,只是在执行同步操作的时候需要传入提交form的id,如editor.sync(myFormID)即可,其他同场景二。还可以使用editor.getContent()方法手动设置。 from:http://www.ueditorbbs.com/forum.php?mod=viewthread&tid=17618&extra=&ordertype=2
View Details可以使用ctrl + shift + f 来格式化代码; 可以使用安装插件wordwrap来实现代码的自动换行:Help ->Install new Software->work with,点击Add,输入 name:wordwrap url:http://ahtik.com/eclipse-update/ 安装成功后重启eclipse from:http://liangfangli86.blog.163.com/blog/static/9684863120116183727729/
View Details假如要Google Play上做一个最失败的案例,那最好的秘诀就是界面奇慢无比、耗电、耗内存。接下来就会得到用户的消极评论,最后名声也就臭了。即使你的应用设计精良、创意无限也没用。 耗电或者内存占用等影响产品效率的每一个问题都会影响App的成功。这就是为什么在开发中确保最优化、运行流畅而且不会使Android系统出问题 是至关重要的了。这里不需要讨论高效编程,因为我们不会关心你写的代码是否能够经得起测试。即使高效的代码也是需要时间来运行。今天这篇文章我们就讲讲怎 么尽可能地缩短运行时间,以及如何开发用户喜欢的App。 高效地利用线程 建议一:怎么在后台取消一些线程中的动作 我们知道App运行过程中所有的操作都默认在主线程(UI线程)中进行的,这样App的响应速度就会受到影响。会导致程序陷入卡顿、死掉甚至会发生系统错误。 为了加快响应速度,需要把费时的操作(比如网络请求、数据库操作或者复杂的计算)从主线程移动到一个单独的线程中。最高效的方式就是在类这一级完成 这项操作,可以使用AsyncTask或者IntentService来创建后台操作。如果选择使用IntentService,它会在需要的时候启动起 来,然后通过一个工作线程来处理请求(Intent)。 使用IntentService时需要注意以下几点限制: 这个类不要给UI传递信息,如果要向用户展示处理结果信息请用Activity; 每次只能处理一个请求; 每一个处理请求过程都不能中断; 建议二:怎么保持响应不发生ANR 从UI线程中移除费时操作这个方式还可以防止用户操作出现系统不响应(ANR)对话框。需要做的就是继承AsyncTask来创建一个后台工作线程,并实现doInBackground()方法。 还有一种方式就是自己创建一个Thread类或者HandlerThread类。需要注意这样也会使App变慢,因为默认的线程优先级和主线程的优先级是一样的,除非你明确设定线程的优先级。 建议三:怎么在线程中初始化查询操作 当查询操作正在后台处理时,展示数据也不是即时的,但是你可以使用CursorLoader对象来加快速度,这个操作可以使Activity和用户之间的互动不受影响。 使用这个对象后,你的App会为ContentProvider初始化一个独立的后台线程进行查询,当查询结束后就会给调用查询的Activity返回结果。 建议四:其它需要注意的方面 使用StrictMode来检查UI线程中可能潜在的费时操作; 使用一些特殊的工具如Systrace或者Traceview来寻找在你的应用中的瓶颈; 用进度条向用户展示操作进度; 如果初始化操作很费时,请展示一个欢迎界面。 优化设备的电池寿命 如果应用很费电,请不要责怪用户卸载了你的应用。对于电池使用来说,主要费电情况如下: 更新数据时经常唤醒程序; 用EDGE或者3G来传递数据; 文本数据转换,进行非JIT正则表达式操作。 建议五:怎么优化网络 如果没有网络连接,请让你的应用跳过网络操作;只在有网络连接并且无漫游的情况下更新数据; 选择兼容的数据格式,把含有文本数据和二进制数据的请求全部转化成二进制数据格式请求; 使用高效的转换工具,多考虑使用流式转换工具,少用树形的转换工具; 为了更快的用户体验,请减少重复访问服务器的操作; 如果可以的话,请使用framework的GZIP库来压缩文本数据以高效使用CPU资源。 建议六:怎么优化应用在前端的工作 如果考虑使用wakelocks,尽量设置为最小的级别; 为了防止潜在的bug导致的电量消耗,请明确指定超时时间; 启用 android:keepScreenOn属性; 除了系统的GC操作,多考虑手动回收Java对象,比如XmlPullParserFactory和BitmapFactory。还有正则表达式的Matcher.reset(newString)操作、StringBuilder.setLength(0)操作; 要注意同步的问题,尽管在主线程中是安全的; 在Listview中要多采用重复利用策略; 如果允许的话多使用粗略的网络定位而不用GPS,对比一下GPS需要1mAh(25s * 140 mA),而一般网络只用0.1mAh(2s * 180mA); 确保注销GPS的位置更新操作,因为这个更新操作在onPause()中也是会继续的。当所有的应用都注销了这个操作,用户可以在系统设置中重新启用GPS而不浪费电量; 请考虑在大量数理运算中使用低精度变量并在用DisplayMetrics进行DPI任务时缓存变量值; 建议七:怎么优化工作在前台的应用 请确保service生命周期都是短暂的,因为每个进程都需要2MB的内存,而在前台程序需要内存时也会重新启动; 保持内存的使用量不要太大; 如果要应用每30分钟更新一次,请在设备处于唤醒状态下进行; Service在pull或者sleep状态都是不好的,这就是为什么在服务结束时要使用AlarmManager或者配置属性stopSelf()的原因。 建议八:其它注意事项 在进行整体更新之前检查电池的状态和网络状态,等待最好的状态在进行大幅度装换操作; 让用户看到用电情况,比如更新周期,后台操作的时候; 实现低内存占用UI 建议九:怎么找到布局显示问题 当我们为布局单独创建UI的时候,就是在创建滥用内存的App,它在UI中会出现可恶的延时。要实现一个流畅的、低内存占用的UI,第一步就是搜索 你的应用找出潜在的瓶颈布局。使用Android SDK/tools/中自带的Hierarchy Viewer Tool工具。 还有一个很好的工具就是Lint,它会扫描应用的源码去寻找可能存在的bug,并为控件结果进行优化。 建议十:如何解决问题 如果布局显示结果发现了问题,你可以考虑简化布局结构。可以把LinearLayout类型转化成RelativeLayout类型,降低布局的层级结构。 做到更加完美并不断优化 尽管以上的每条建议看起来都是很小的改进,但是如果它能成为你日常代码的一部分,那么你就会看到意想不到的结果。要让Google Play看到更多杰出的、流畅的、更快速、更省电的应用,向Android走向完美的目标迈进一步。 原文链接: azoft 翻译: 伯乐在线 – chris 译文链接: http://blog.jobbole.com/64279/ from:http://www.oschina.net/news/50413/android-application-development-tips
View Details